Replaced plots swing rendering by javafx

This commit is contained in:
Alexander Nozik 2016-05-15 16:26:38 +03:00
parent 468fbb873f
commit d344922d3f
16 changed files with 127 additions and 2331 deletions

View File

@ -1,131 +0,0 @@
/*
* Copyright 2015 Alexander Nozik.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package inr.numass.readvac;
import hep.dataforge.context.Context;
import hep.dataforge.context.GlobalContext;
import static hep.dataforge.context.GlobalContext.out;
import hep.dataforge.io.MetaFileReader;
import hep.dataforge.meta.Meta;
import hep.dataforge.storage.api.Storage;
import hep.dataforge.storage.commons.StorageManager;
import java.io.File;
import java.io.IOException;
import java.util.Locale;
import org.apache.commons.cli.CommandLine;
import org.apache.commons.cli.CommandLineParser;
import org.apache.commons.cli.DefaultParser;
import org.apache.commons.cli.HelpFormatter;
import org.apache.commons.cli.Options;
import org.apache.commons.cli.ParseException;
/**
*
* @author Darksnake
*/
public class Main {
static String name;
// static volatile boolean stopFlag = false;
/**
* @param args the command line arguments
* @throws java.lang.Exception
*/
public static void main(String[] args) throws Exception {
Locale.setDefault(Locale.US);
new StorageManager().startGlobal();
Meta config = getAnnotation(args);
runConfig(config);
// System.exit(0);//на всякий случай, чтобы закрыть все боковые потоки
}
public static void runConfig(Meta config) throws Exception {
// VACManager daemon;
// //Определяем, является считывает ли сервер из файла или из com порта
// boolean direct = config.getBoolean("direct", true);
//Префикс сеанса
String prefix = config.getString("run", name);
Storage server = setupServer(GlobalContext.instance(), config);
// if (direct) {
// daemon = VACManager.fromSerial(server, getSerialConfig(config), prefix);
// } else {
// daemon = VACManager.fromDirectory(server, getDataPath(config), prefix);
// }
VACManager daemon = VACManager.fromSerial(server, prefix, getSerialConfig(config));
daemon.start();
}
private static Meta getSerialConfig(Meta config) {
return config.getNode("serialconfig", config);
}
private static Storage setupServer(Context context, Meta config) {
Meta storageConfig = config.getNode("storage");
return context.provide("storage", StorageManager.class).buildStorage(storageConfig);
}
// private static String getDataPath(Meta config) {
// return config.getString("datapath", "D:\\temp\\test");
// }
private static Options prepareOptions() {
Options options = new Options();
options.addOption("c", "config", true, "Configuration file path");
// options.addOption("d", "dir", true, "Directory with data files");
options.addOption("n", "name", true, "Run name");
options.addOption("h", "home", true, "Working directory");
// options.addOption("t", "target", true, "Target data file");
return options;
}
private static Meta getAnnotation(String[] cli) throws IOException, ParseException, java.text.ParseException {
String configPath;
Options options = prepareOptions();
if (cli.length == 0) {
HelpFormatter formatter = new HelpFormatter();
formatter.printHelp("java -jar readVAC.jar [OPTIONS]", options);
out().println("Trying to use default config location...");
configPath = "vac-config.xml";
} else {
CommandLineParser parser = new DefaultParser();
CommandLine line;
// parse the command line arguments
line = parser.parse(options, cli);
if (line.hasOption("h")) {
System.setProperty("user.dir", line.getOptionValue("h"));
}
if (line.hasOption("n")) {
name = line.getOptionValue("n");
}
configPath = line.getOptionValue("c", "config.xml");
}
File configFile = new File(configPath);
return MetaFileReader.read(configFile);
}
}

View File

@ -1,40 +0,0 @@
/*
* Copyright 2015 Alexander Nozik.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package inr.numass.readvac;
/**
*
* @author Darksnake
*/
class P1ControlException extends Exception {
/**
* Creates a new instance of <code>p1ControlException</code> without detail
* message.
*/
public P1ControlException() {
}
/**
* Constructs an instance of <code>p1ControlException</code> with the
* specified detail message.
*
* @param msg the detail message.
*/
public P1ControlException(String msg) {
super(msg);
}
}

View File

@ -1,36 +0,0 @@
/*
* Copyright 2015 Alexander Nozik.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package inr.numass.readvac;
/**
*
* @author Darksnake
*/
public class ResponseParseException extends Exception {
String response;
public ResponseParseException(String response) {
this.response = response;
}
public ResponseParseException(String response, String message) {
super(message);
this.response = response;
}
}

View File

@ -1,81 +0,0 @@
/*
* Copyright 2015 Alexander Nozik.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package inr.numass.readvac;
import java.io.IOException;
import java.io.OutputStream;
import javax.swing.JTextArea;
import javax.swing.SwingUtilities;
import javax.swing.text.BadLocationException;
import javax.swing.text.Utilities;
import org.slf4j.LoggerFactory;
/**
*
* @author Darksnake
*/
public class TextAreaOutputStream extends OutputStream {
private static final int MAXLINES = 500;
private final JTextArea textArea;
private final StringBuilder sb = new StringBuilder();
private final String title;
// public static IOManager getTextAreaIO(Context context, JTextArea area){
// return new BasicIOManager(context, new TextAreaOutputStream(area, "system"));
// }
public TextAreaOutputStream(final JTextArea textArea, String title) {
this.textArea = textArea;
this.title = title;
sb.append(title).append("> ");
}
@Override
public void flush() {
}
@Override
public void close() {
}
@Override
public void write(int b) throws IOException {
if (b == '\r') {
return;
}
if (b == '\n') {
final String text = sb.toString() + "\n";
SwingUtilities.invokeLater(() -> {
textArea.append(text);
while (textArea.getLineCount() >= MAXLINES) {
try {
textArea.getDocument().remove(0, Utilities.getRowEnd(textArea, 1));
} catch (BadLocationException ex) {
LoggerFactory.getLogger(getClass()).error(null, ex);
break;
}
}
});
sb.setLength(0);
sb.append(title).append("> ");
return;
}
sb.append((char) b);
}
}

View File

@ -1,412 +0,0 @@
/*
* Copyright 2015 Alexander Nozik.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package inr.numass.readvac;
import hep.dataforge.meta.Meta;
import hep.dataforge.tables.DataPoint;
import hep.dataforge.tables.MapPoint;
import hep.dataforge.values.Value;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.util.Iterator;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import jssc.SerialPort;
import jssc.SerialPortException;
import jssc.SerialPortTimeoutException;
import org.slf4j.LoggerFactory;
/**
*
* @author Darksnake
*/
public class VACDeviceReader implements Iterator<DataPoint>, AutoCloseable {
// private int timeout = 100;
private final int maxChars = 50;
private static final String CM32Query = "MES R PM 1\r\n";
private static final String MQuery = ":010300000002FA\r\n";
private static final String P1Query = "@253PR5?;FF";
SerialPort p2Port;
SerialPort p3Port;
SerialPort p1Port;
SerialPort pxPort;
Lock p1Lock;
Lock p2Lock;
Lock p3Lock;
Lock pxLock;
Meta p1Config;
Meta p2Config;
Meta p3Config;
Meta pxConfig;
private boolean p1PowerOn = false;
public VACDeviceReader(String p2, String p3, String p1, String px) throws SerialPortException {
setupPorts(p2, p3, p1, px);
}
public VACDeviceReader(Meta serialConfig) throws SerialPortException {
String p2 = serialConfig.getString("P2", null);
String p3 = serialConfig.getString("P3", null);
String p1 = serialConfig.getString("P1", null);
String px = serialConfig.getString("Px", p1);
// this.timeout = serialConfig.getInt("timeout", timeout);
setupPorts(p2, p3, p1, px);
}
public boolean setP1PowerStateOn(boolean state) throws SerialPortException, ResponseParseException, P1ControlException {
p1PowerOn = getP1PowerState();
if (state == p1PowerOn) {
//Возвращаем то, что есть
return p1PowerOn;
} else {
if (state == true) {
// String ans = talkMKS(p1Port, "@253ENC!OFF;FF");
// if (!ans.equals("OFF")) {
// LoggerFactory.getLogger(getClass()).warn("The @253ENC!OFF;FF command is not working");
// }
String ans = talkMKS(p1Port, "@253FP!ON;FF");
if (!ans.equals("ON")) {
throw new P1ControlException("Can't set P1 cathod power state");
}
} else {
String ans = talkMKS(p1Port, "@253FP!OFF;FF");
if (!ans.equals("OFF")) {
throw new P1ControlException("Can't set P1 cathod power state");
}
}
p1PowerOn = getP1PowerState();
return p1PowerOn;
}
}
public boolean isP1Available() {
try {
return !talkMKS(p1Port, "@253T?;FF").isEmpty();
} catch (SerialPortException | ResponseParseException ex) {
return false;
}
}
private String talkMKS(SerialPort port, String request) throws SerialPortException, ResponseParseException {
try {
p1Lock.lock();
if (!port.isOpened()) {
port.openPort();
}
port.purgePort(SerialPort.PURGE_RXCLEAR | SerialPort.PURGE_TXCLEAR);
port.writeString(request);
LoggerFactory.getLogger(port.getPortName()).info("send> " + request.trim());
String answer = readPort(p1Port, ";FF", 100);
LoggerFactory.getLogger(port.getPortName()).info("recieve> " + answer.trim());
if (answer.isEmpty()) {
throw new ResponseParseException(answer);
}
Matcher match = Pattern.compile("@253ACK(.*);FF").matcher(answer);
if (match.matches()) {
return match.group(1);
} else {
throw new ResponseParseException(answer);
}
} finally {
p1Lock.unlock();
}
}
public boolean getP1PowerState() throws SerialPortException, ResponseParseException {
String answer = talkMKS(p1Port, "@253FP?;FF");
return answer.equals("ON");
}
/**
* Считываем строку из порта пока не найдем delimeter или не потратим
* timeout времени. Если случается таймаут, то возвращается null
*
* @param port
* @param delimeter
* @return
* @throws SerialPortException
*/
private String readPort(SerialPort port, String delimeter, int timeout) throws SerialPortException {
String res = new String();
Instant start = Instant.now();
port.purgePort(SerialPort.PURGE_RXCLEAR | SerialPort.PURGE_TXCLEAR);
while (res.length() < maxChars) {
try {
res += port.readString(1, timeout);
} catch (SerialPortTimeoutException ex) {
return "";
}
if (start.until(Instant.now(), ChronoUnit.MILLIS) > timeout) {
return "";
}
if (res.endsWith(delimeter)) {
return res;
}
}
return "";
}
@Override
public void close() throws Exception {
if (p1Port.isOpened()) {
p1Port.closePort();
}
if (pxPort.isOpened()) {
pxPort.closePort();
}
if (p2Port.isOpened()) {
p2Port.closePort();
}
if (p3Port.isOpened()) {
p3Port.closePort();
}
try {
this.setP1PowerStateOn(false);
} catch (P1ControlException ex) {
LoggerFactory.getLogger(getClass()).warn("Can't turn of the power on P1");
}
}
private void setupPorts(String p2, String p3, String p1, String px) {
try {
if (p2 == null) {
p2Port = null;
} else {
p2Port = new SerialPort(p2);
p2Port.openPort();
p2Port.setParams(2400, 8, 1, 0);
p2Lock = new ReentrantLock();
}
} catch (SerialPortException ex) {
p2Port = null;
LoggerFactory.getLogger(getClass()).error("Can't open " + p2, ex);
}
try {
if (p3 == null) {
p3Port = null;
} else {
p3Port = new SerialPort(p3);
p3Port.openPort();
p3Port.setParams(2400, 8, 1, 0);
p3Lock = new ReentrantLock();
}
} catch (SerialPortException ex) {
p2Port = null;
LoggerFactory.getLogger(getClass()).error("Can't open " + p3, ex);
}
try {
if (p1 == null) {
p1Port = null;
} else {
p1Port = new SerialPort(p1);
p1Port.openPort();
p1Port.setParams(9600, 8, 1, 0);
p1Lock = new ReentrantLock();
}
} catch (SerialPortException ex) {
p2Port = null;
LoggerFactory.getLogger(getClass()).error("Can't open " + p1, ex);
}
if (px == null) {
pxPort = null;
} else {
if (px.equals(p1)) {
pxPort = p1Port;
pxLock = p1Lock;
} else {
try {
pxPort = new SerialPort(px);
pxPort.openPort();
pxPort.setParams(9600, 8, 1, 0);
pxLock = new ReentrantLock();
} catch (SerialPortException ex) {
p2Port = null;
LoggerFactory.getLogger(getClass()).error("Can't open " + px, ex);
}
}
}
}
private Value readCM(SerialPort port) {
try {
if (!port.isOpened()) {
port.openPort();
}
port.purgePort(SerialPort.PURGE_RXCLEAR | SerialPort.PURGE_TXCLEAR);
port.writeString(CM32Query);
LoggerFactory.getLogger(port.getPortName()).info("send> " + CM32Query.trim());
// try {
// Thread.sleep(200);
// } catch (InterruptedException ex) {
// Logger.getLogger(VACDeviceReader.class.getName()).log(Level.SEVERE, null, ex);
// }
String answer = readPort(port, "T--", 400);
LoggerFactory.getLogger(port.getPortName()).info("recieve> " + answer.trim());
if (answer.isEmpty()) {
return Value.of("EMPTY");
}
if (answer.indexOf("PM1:mbar") < -1) {
return Value.of("PARSE");
}
if (answer.substring(14, 17).equals("OFF")) {
return Value.of("OFF");
}
return Value.of(Double.parseDouble(answer.substring(14, 17) + answer.substring(19, 23)));
} catch (SerialPortException ex) {
return Value.of("COM_ERR");
}/* catch (SerialPortTimeoutException ex) {
return Value.of("COM_TIMEOUT");
}*/
}
private Value readP1() {
if (p1Port == null) {
return Value.of("NO_CON");
}
try {
String answer = talkMKS(p1Port, P1Query);
if (answer == null || answer.isEmpty()) {
return Value.of("EMPTY");
}
double res = Double.parseDouble(answer);
if (res <= 0) {
return Value.of("OFF");
} else {
return Value.of(res);
}
} catch (SerialPortException ex) {
return Value.of("COM_ERR");
} catch (ResponseParseException ex) {
return Value.of("PARSE");
}
}
private Value readPx() {
if (pxPort == null) {
return Value.of("NO_CON");
}
try {
if (!pxPort.isOpened()) {
pxPort.openPort();
}
pxPort.purgePort(SerialPort.PURGE_RXCLEAR | SerialPort.PURGE_TXCLEAR);
pxPort.writeString(MQuery);
LoggerFactory.getLogger(pxPort.getPortName()).info("send> " + MQuery.trim());
String answer = readPort(pxPort, "\r\n", 100);
LoggerFactory.getLogger(pxPort.getPortName()).info("recieve> " + answer.trim());
if (answer.isEmpty()) {
return Value.of("EMPTY");
}
Matcher match = Pattern.compile(":010304(\\w{4})(\\w{4})..\r\n").matcher(answer);
if (match.matches()) {
double base = (double) (Integer.parseInt(match.group(1), 16)) / 10d;
int exp = Integer.parseInt(match.group(2), 16);
if (exp > 32766) {
exp = exp - 65536;
}
BigDecimal res = BigDecimal.valueOf(base * Math.pow(10, exp));
res = res.setScale(4, RoundingMode.CEILING);
return Value.of(res);
} else {
return Value.of("PARSE");
}
} catch (SerialPortException ex) {
return Value.of("COM_ERR");
}
}
private Value readP2() {
if (p2Port == null) {
return Value.of("NO_CON");
}
try {
p2Lock.lock();
return readCM(p2Port);
} finally {
p2Lock.unlock();
}
}
private Value readP3() {
if (p3Port == null) {
return Value.of("NO_CON");
}
try {
p3Lock.lock();
return readCM(p3Port);
} finally {
p3Lock.unlock();
}
}
@Override
public boolean hasNext() {
return true;
}
@Override
public DataPoint next() {
Value p1 = readP1();
Value p2 = readP2();
Value p3 = readP3();
Value px = readPx();
Value time = Value.of(Instant.now().truncatedTo(ChronoUnit.SECONDS));
return new MapPoint(VACManager.names, time, p1, p2, p3, px);
}
}
//P2, P3:
//Q:"MES R PM 1\r\n"
//A:"PM1:mbar : 2.3 E-03:T--
//"
//
//P1:
//Q:"@253PR4?;FF"
//A:"@253ACK3.891E+1;FF"
//
//Px:
//Q:":010300000002FA\r\n"
//A:":0103040014FFFEE7"
//нужно брать символы с 8 по 12

View File

@ -1,142 +0,0 @@
/*
* Copyright 2015 Alexander Nozik.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package inr.numass.readvac;
import hep.dataforge.io.LineIterator;
import hep.dataforge.tables.DataPoint;
import hep.dataforge.tables.MapPoint;
import hep.dataforge.tables.PointParser;
import java.io.File;
import java.io.FileNotFoundException;
import java.time.Instant;
import java.time.LocalDateTime;
import java.time.ZoneOffset;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
*
* @author Darksnake
*/
public class VACFileReader implements Iterator<DataPoint> {
private static final DateTimeFormatter formatter = DateTimeFormatter.ofPattern("dd.MM.yyyy HH:mm:ss");//14.04.2014 21:30:10
public static VACFileReader fromDirectory(String dir) throws FileNotFoundException {
File directory = new File(dir);
String[] list = directory.list((File dir1, String name) -> name.startsWith("VacTMS") && name.endsWith(".txt"));
if(list.length == 0){
throw new FileNotFoundException("Data files not found in the given directory");
}
Arrays.sort(list);
return new VACFileReader(new File(directory,list[list.length-1]));
}
public static VACFileReader fromFile(String file) throws FileNotFoundException {
return new VACFileReader(new File(file));
}
private final LineIterator iterator;
private final PointParser parser;
private VACFileReader(File vacFile) throws FileNotFoundException {
this.iterator = new LineIterator(vacFile);
iterator.next();
parser = new LikhovidVACParser();
}
public VACFileReader(File vacFile, PointParser parser) throws FileNotFoundException {
this.iterator = new LineIterator(vacFile);
iterator.next();
this.parser = parser;
}
public DataPoint get(Instant time) {
throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
}
public DataPoint getLast() {
DataPoint point = null;
while (hasNext()) {
point = next();
}
return point;
}
@Override
public boolean hasNext() {
return iterator.hasNext();
}
@Override
public DataPoint next() {
if (iterator.hasNext()) {
return parser.parse(iterator.next());
} else {
return null;
}
}
public List<DataPoint> updateFrom(Instant from) {
List<DataPoint> res = new ArrayList<>();
while (iterator.hasNext()) {
DataPoint point = next();
if (point != null && point.getValue("timestamp").timeValue().isAfter(from)) {
res.add(point);
}
}
return res;
}
public List<DataPoint> updateFrom() {
List<DataPoint> res = new ArrayList<>();
while (iterator.hasNext()) {
DataPoint point = next();
if (point != null) {
res.add(point);
}
}
return res;
}
private static class LikhovidVACParser implements PointParser {
static final Pattern pattern = Pattern.compile("(\\S* \\S*)\\s*(\\S*);\\s*(\\S*)\\s*(\\S*)\\s*(\\S*)");
@Override
public DataPoint parse(String str) {
Matcher matcher = pattern.matcher(str);
if(!matcher.matches()){
return null;
}
LocalDateTime dt = LocalDateTime.parse(matcher.group(1), formatter);
Instant time = dt.toInstant(ZoneOffset.ofHours(0));
String p1 = matcher.group(2);
String p2 = matcher.group(3);
String p3 = matcher.group(4);
String px = matcher.group(5);
return new MapPoint(VACManager.names, new Object[]{time, p1, p2, p3, px});
}
}
}

View File

@ -1,395 +0,0 @@
<?xml version="1.0" encoding="UTF-8" ?>
<Form version="1.9" maxVersion="1.9" type="org.netbeans.modules.form.forminfo.JFrameFormInfo">
<Properties>
<Property name="defaultCloseOperation" type="int" value="2"/>
<Property name="minimumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="[800, 180]"/>
</Property>
<Property name="name" type="java.lang.String" value="mainFrame" noResource="true"/>
<Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="[1052, 600]"/>
</Property>
</Properties>
<AccessibilityProperties>
<Property name="AccessibleContext.accessibleParent" type="javax.accessibility.Accessible" editor="org.netbeans.modules.form.ComponentChooserEditor">
<ComponentRef name="Form"/>
</Property>
</AccessibilityProperties>
<SyntheticProperties>
<SyntheticProperty name="formSizePolicy" type="int" value="1"/>
<SyntheticProperty name="generateCenter" type="boolean" value="false"/>
</SyntheticProperties>
<AuxValues>
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="0"/>
<AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
<AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
<AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/>
<AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="false"/>
<AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="1"/>
<AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/>
<AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/>
<AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/>
<AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,0,-33,0,0,4,28"/>
</AuxValues>
<Layout class="org.netbeans.modules.form.compat2.layouts.DesignBoxLayout">
<Property name="axis" type="int" value="1"/>
</Layout>
<SubComponents>
<Container class="javax.swing.JPanel" name="valuesPanel">
<Properties>
<Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor">
<Border info="org.netbeans.modules.form.compat2.border.BevelBorderInfo">
<BevelBorder/>
</Border>
</Property>
<Property name="minimumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="[0, 90]"/>
</Property>
</Properties>
<Layout>
<DimensionLayout dim="0">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace min="-2" pref="15" max="-2" attributes="0"/>
<Group type="103" groupAlignment="0" max="-2" attributes="0">
<Component id="jLabel5" max="32767" attributes="0"/>
<Component id="timeLabel" pref="180" max="32767" attributes="0"/>
</Group>
<EmptySpace pref="122" max="32767" attributes="0"/>
<Group type="103" groupAlignment="0" max="-2" attributes="0">
<Component id="p1Label" max="32767" attributes="0"/>
<Component id="jLabel1" min="-2" pref="81" max="-2" attributes="0"/>
</Group>
<EmptySpace pref="104" max="32767" attributes="0"/>
<Group type="103" groupAlignment="0" max="-2" attributes="0">
<Component id="p2Label" alignment="0" max="32767" attributes="0"/>
<Component id="jLabel2" alignment="0" min="-2" pref="81" max="-2" attributes="0"/>
</Group>
<EmptySpace pref="104" max="32767" attributes="0"/>
<Group type="103" groupAlignment="0" max="-2" attributes="0">
<Component id="p3Label" alignment="0" max="32767" attributes="0"/>
<Component id="jLabel3" alignment="0" min="-2" pref="81" max="-2" attributes="0"/>
</Group>
<EmptySpace pref="106" max="32767" attributes="0"/>
<Group type="103" groupAlignment="0" max="-2" attributes="0">
<Component id="pxLabel" alignment="0" max="32767" attributes="0"/>
<Component id="jLabel4" alignment="0" min="-2" pref="81" max="-2" attributes="0"/>
</Group>
<EmptySpace pref="53" max="32767" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
<DimensionLayout dim="1">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace max="-2" attributes="0"/>
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" attributes="0">
<Component id="jLabel4" min="-2" max="-2" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="pxLabel" min="-2" max="-2" attributes="0"/>
</Group>
<Group type="103" groupAlignment="1" attributes="0">
<Group type="102" attributes="0">
<Component id="jLabel3" min="-2" max="-2" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="p3Label" min="-2" max="-2" attributes="0"/>
</Group>
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" attributes="0">
<Component id="jLabel2" min="-2" max="-2" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="p2Label" min="-2" max="-2" attributes="0"/>
</Group>
<Group type="102" attributes="0">
<Group type="103" groupAlignment="3" attributes="0">
<Component id="jLabel1" alignment="3" min="-2" max="-2" attributes="0"/>
<Component id="jLabel5" alignment="3" min="-2" max="-2" attributes="0"/>
</Group>
<EmptySpace max="-2" attributes="0"/>
<Group type="103" groupAlignment="3" attributes="0">
<Component id="p1Label" alignment="3" min="-2" max="-2" attributes="0"/>
<Component id="timeLabel" alignment="3" min="-2" max="-2" attributes="0"/>
</Group>
</Group>
</Group>
</Group>
</Group>
<EmptySpace max="-2" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
</Layout>
<SubComponents>
<Component class="javax.swing.JLabel" name="jLabel1">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="0"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="P1"/>
</Properties>
</Component>
<Component class="javax.swing.JLabel" name="p1Label">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="1"/>
</Property>
<Property name="foreground" type="java.awt.Color" editor="org.netbeans.beaninfo.editors.ColorEditor">
<Color blue="0" green="0" id="red" palette="1" red="ff" type="palette"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="EMPTY"/>
</Properties>
</Component>
<Component class="javax.swing.JLabel" name="jLabel2">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="0"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="P2"/>
</Properties>
</Component>
<Component class="javax.swing.JLabel" name="p2Label">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="1"/>
</Property>
<Property name="foreground" type="java.awt.Color" editor="org.netbeans.beaninfo.editors.ColorEditor">
<Color blue="ff" green="0" id="blue" palette="1" red="0" type="palette"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="EMPTY"/>
</Properties>
</Component>
<Component class="javax.swing.JLabel" name="jLabel3">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="0"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="P3"/>
</Properties>
</Component>
<Component class="javax.swing.JLabel" name="p3Label">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="1"/>
</Property>
<Property name="foreground" type="java.awt.Color" editor="org.netbeans.beaninfo.editors.ColorEditor">
<Color blue="0" green="ff" id="green" palette="1" red="0" type="palette"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="EMPTY"/>
</Properties>
</Component>
<Component class="javax.swing.JLabel" name="jLabel4">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="0"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="Px"/>
</Properties>
</Component>
<Component class="javax.swing.JLabel" name="pxLabel">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="1"/>
</Property>
<Property name="foreground" type="java.awt.Color" editor="org.netbeans.beaninfo.editors.ColorEditor">
<Color blue="ff" green="0" id="magenta" palette="1" red="ff" type="palette"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="EMPTY"/>
</Properties>
</Component>
<Component class="javax.swing.JLabel" name="timeLabel">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="1"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="EMPTY"/>
</Properties>
</Component>
<Component class="javax.swing.JLabel" name="jLabel5">
<Properties>
<Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor">
<Font name="Tahoma" size="24" style="0"/>
</Property>
<Property name="horizontalAlignment" type="int" value="0"/>
<Property name="text" type="java.lang.String" value="time"/>
</Properties>
</Component>
</SubComponents>
</Container>
<Container class="javax.swing.JPanel" name="optionsPanel">
<Properties>
<Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor">
<Border info="org.netbeans.modules.form.compat2.border.BevelBorderInfo">
<BevelBorder/>
</Border>
</Property>
<Property name="maximumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="[32767, 50]"/>
</Property>
<Property name="minimumSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="[0, 50]"/>
</Property>
<Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor">
<Dimension value="[1052, 50]"/>
</Property>
</Properties>
<Layout>
<DimensionLayout dim="0">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace min="-2" pref="4" max="-2" attributes="0"/>
<Component id="jLabel6" min="-2" max="-2" attributes="0"/>
<EmptySpace type="unrelated" max="-2" attributes="0"/>
<Component id="delayBox" min="-2" max="-2" attributes="0"/>
<EmptySpace min="-2" pref="32" max="-2" attributes="0"/>
<Component id="jLabel7" min="-2" max="-2" attributes="0"/>
<EmptySpace max="-2" attributes="0"/>
<Component id="rangeBox" min="-2" max="-2" attributes="0"/>
<EmptySpace pref="427" max="32767" attributes="0"/>
<Component id="p1Power" min="-2" max="-2" attributes="0"/>
<EmptySpace min="-2" pref="60" max="-2" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
<DimensionLayout dim="1">
<Group type="103" groupAlignment="0" attributes="0">
<Group type="102" alignment="0" attributes="0">
<EmptySpace max="-2" attributes="0"/>
<Group type="103" groupAlignment="3" attributes="0">
<Component id="jLabel7" alignment="3" min="-2" max="-2" attributes="0"/>
<Component id="rangeBox" alignment="3" min="-2" max="-2" attributes="0"/>
<Component id="delayBox" alignment="3" min="-2" max="-2" attributes="0"/>
<Component id="jLabel6" alignment="3" min="-2" max="-2" attributes="0"/>
<Component id="p1Power" alignment="3" min="-2" max="-2" attributes="0"/>
</Group>
<EmptySpace min="-2" pref="40" max="-2" attributes="0"/>
</Group>
</Group>
</DimensionLayout>
</Layout>
<SubComponents>
<Component class="javax.swing.JLabel" name="jLabel6">
<Properties>
<Property name="text" type="java.lang.String" value="&#x427;&#x430;&#x441;&#x442;&#x43e;&#x442;&#x430; &#x43e;&#x431;&#x43d;&#x43e;&#x432;&#x43b;&#x435;&#x43d;&#x438;&#x44f; (&#x441;):"/>
</Properties>
</Component>
<Component class="javax.swing.JComboBox" name="delayBox">
<Properties>
<Property name="model" type="javax.swing.ComboBoxModel" editor="org.netbeans.modules.form.editors2.ComboBoxModelEditor">
<StringArray count="5">
<StringItem index="0" value="1"/>
<StringItem index="1" value="5"/>
<StringItem index="2" value="10"/>
<StringItem index="3" value="30"/>
<StringItem index="4" value="60"/>
</StringArray>
</Property>
<Property name="selectedIndex" type="int" value="1"/>
</Properties>
<Events>
<EventHandler event="itemStateChanged" listener="java.awt.event.ItemListener" parameters="java.awt.event.ItemEvent" handler="delayBoxItemStateChanged"/>
</Events>
</Component>
<Component class="javax.swing.JComboBox" name="rangeBox">
<Properties>
<Property name="model" type="javax.swing.ComboBoxModel" editor="org.netbeans.modules.form.editors2.ComboBoxModelEditor">
<StringArray count="5">
<StringItem index="0" value="10"/>
<StringItem index="1" value="30"/>
<StringItem index="2" value="60"/>
<StringItem index="3" value="180"/>
<StringItem index="4" value="300"/>
</StringArray>
</Property>
<Property name="selectedIndex" type="int" value="2"/>
<Property name="toolTipText" type="java.lang.String" value=""/>
</Properties>
<Events>
<EventHandler event="itemStateChanged" listener="java.awt.event.ItemListener" parameters="java.awt.event.ItemEvent" handler="rangeBoxItemStateChanged"/>
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="rangeBoxActionPerformed"/>
</Events>
</Component>
<Component class="javax.swing.JLabel" name="jLabel7">
<Properties>
<Property name="text" type="java.lang.String" value="&#x41c;&#x430;&#x43a;&#x441;&#x438;&#x43c;&#x430;&#x43b;&#x44c;&#x43d;&#x44b;&#x439; &#x434;&#x438;&#x430;&#x43f;&#x430;&#x437;&#x43e;&#x43d; (&#x43c;&#x438;&#x43d;):"/>
</Properties>
</Component>
<Component class="javax.swing.JToggleButton" name="p1Power">
<Properties>
<Property name="text" type="java.lang.String" value="&#x425;&#x43e;&#x43b;&#x43e;&#x434;&#x43d;&#x44b;&#x439; &#x43a;&#x430;&#x442;&#x43e;&#x434; &#x43d;&#x430; P1"/>
</Properties>
<Events>
<EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="p1PowerActionPerformed"/>
</Events>
</Component>
</SubComponents>
</Container>
<Container class="javax.swing.JSplitPane" name="split">
<Properties>
<Property name="orientation" type="int" value="0"/>
<Property name="resizeWeight" type="double" value="1.0"/>
<Property name="alignmentX" type="float" value="0.5"/>
<Property name="alignmentY" type="float" value="0.5"/>
<Property name="oneTouchExpandable" type="boolean" value="true"/>
</Properties>
<Layout class="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout"/>
<SubComponents>
<Container class="javax.swing.JPanel" name="chartPannel">
<Properties>
<Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor">
<Border info="org.netbeans.modules.form.compat2.border.BevelBorderInfo">
<BevelBorder/>
</Border>
</Property>
<Property name="autoscrolls" type="boolean" value="true"/>
</Properties>
<Constraints>
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout" value="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription">
<JSplitPaneConstraints position="top"/>
</Constraint>
</Constraints>
<Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/>
</Container>
<Container class="javax.swing.JScrollPane" name="scroll">
<Constraints>
<Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout" value="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription">
<JSplitPaneConstraints position="bottom"/>
</Constraint>
</Constraints>
<Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/>
<SubComponents>
<Component class="javax.swing.JTextArea" name="consoleBox">
<Properties>
<Property name="editable" type="boolean" value="false"/>
<Property name="columns" type="int" value="20"/>
<Property name="lineWrap" type="boolean" value="true"/>
<Property name="rows" type="int" value="5"/>
</Properties>
<AccessibilityProperties>
<Property name="AccessibleContext.accessibleParent" type="javax.accessibility.Accessible" editor="org.netbeans.modules.form.ComponentChooserEditor">
<ComponentRef name="split"/>
</Property>
</AccessibilityProperties>
</Component>
</SubComponents>
</Container>
</SubComponents>
</Container>
</SubComponents>
</Form>

View File

@ -1,542 +0,0 @@
/*
* Copyright 2015 Alexander Nozik.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package inr.numass.readvac;
import ch.qos.logback.classic.LoggerContext;
import ch.qos.logback.classic.spi.ILoggingEvent;
import ch.qos.logback.core.AppenderBase;
import ch.qos.logback.core.encoder.EchoEncoder;
import ch.qos.logback.core.encoder.Encoder;
import hep.dataforge.context.GlobalContext;
import hep.dataforge.io.BasicIOManager;
import hep.dataforge.meta.Meta;
import hep.dataforge.meta.MetaBuilder;
import hep.dataforge.plots.data.DynamicPlottable;
import hep.dataforge.plots.data.DynamicPlottableSet;
import hep.dataforge.plots.jfreechart.JFreeChartFrame;
import hep.dataforge.tables.DataPoint;
import hep.dataforge.values.Value;
import hep.dataforge.values.ValueType;
import java.awt.Dimension;
import java.awt.event.WindowEvent;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.time.LocalDateTime;
import java.time.ZoneId;
import java.time.format.DateTimeFormatter;
import javax.swing.AbstractButton;
import javax.swing.JTextArea;
import javax.swing.SwingUtilities;
import org.jfree.chart.axis.LogarithmicAxis;
import org.jfree.chart.plot.XYPlot;
import org.slf4j.LoggerFactory;
/**
*
* @author Darksnake
*/
public class VACFrame extends javax.swing.JFrame {
private static final DateTimeFormatter formatter = DateTimeFormatter.ofPattern("HH:mm:ss");
public static VACFrame display(VACManager daemon) {
/* Set the Nimbus look and feel */
//<editor-fold defaultstate="collapsed" desc=" Look and feel setting code (optional) ">
/* If Nimbus (introduced in Java SE 6) is not available, stay with the default look and feel.
* For details see http://download.oracle.com/javase/tutorial/uiswing/lookandfeel/plaf.html
*/
try {
for (javax.swing.UIManager.LookAndFeelInfo info : javax.swing.UIManager.getInstalledLookAndFeels()) {
if ("Nimbus".equals(info.getName())) {
javax.swing.UIManager.setLookAndFeel(info.getClassName());
break;
}
}
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | javax.swing.UnsupportedLookAndFeelException ex) {
java.util.logging.Logger.getLogger(VACFrame.class.getName()).log(java.util.logging.Level.SEVERE, null, ex);
}
//</editor-fold>
VACFrame frame = new VACFrame();
frame.daemon = daemon;
boolean p1Available = daemon.p1Available();
frame.p1Power.setEnabled(p1Available);
if (p1Available) {
try {
frame.updateP1PowerState(daemon.getP1PowerState());
} catch (P1ControlException ex) {
LoggerFactory.getLogger("COM-P1").error(ex.getMessage());
}
} else {
frame.p1Power.setText("P1 недоступен");
}
frame.addWindowListener(new java.awt.event.WindowAdapter() {
@Override
public void windowClosing(WindowEvent winEvt) {
try {
daemon.close();
} catch (Exception ex) {
LoggerFactory.getLogger(VACFrame.class).error(null, ex);
}
System.exit(0);
}
});
// /* Create and displayPoint the form */
// SwingUtilities.invokeLater(() -> {
// frame.setVisible(true);
//// frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
// });
frame.setVisible(true);
return frame;
}
private VACManager daemon;
private JFreeChartFrame plotFrame;
private DynamicPlottableSet plottables;
// private int savedSplitHeight = 600;
/**
* Creates new form VACFrame
*/
private VACFrame() {
setTitle("Numass vacuum measurement view");
initComponents();
split.getRightComponent().setMinimumSize(new Dimension());
split.setDividerLocation(1.0);
GlobalContext.instance().setIO(new BasicIOManager(new TextAreaOutputStream(consoleBox, "CONSOLE")));
JTextAreaAppender app = new JTextAreaAppender(consoleBox);
LoggerContext lc = (LoggerContext) LoggerFactory.getILoggerFactory();
app.setContext(lc);
app.start();
lc.getLogger("ROOT").addAppender(app);
plottables = setupPlot();
displayChart();
}
private DynamicPlottableSet setupPlot() {
DynamicPlottable p1 = DynamicPlottable.build("P1", "pressure", "RED", 2.5);
DynamicPlottable p2 = DynamicPlottable.build("P2", "pressure", "BLUE", 2.5);
DynamicPlottable p3 = DynamicPlottable.build("P3", "pressure", "GREEN", 2.5);
DynamicPlottable px = DynamicPlottable.build("Px", "pressure", "MAGENTA", 2.5);
return new DynamicPlottableSet(p1, p2, p3, px);
}
/**
* 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")
// <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
private void initComponents() {
valuesPanel = new javax.swing.JPanel();
jLabel1 = new javax.swing.JLabel();
p1Label = new javax.swing.JLabel();
jLabel2 = new javax.swing.JLabel();
p2Label = new javax.swing.JLabel();
jLabel3 = new javax.swing.JLabel();
p3Label = new javax.swing.JLabel();
jLabel4 = new javax.swing.JLabel();
pxLabel = new javax.swing.JLabel();
timeLabel = new javax.swing.JLabel();
jLabel5 = new javax.swing.JLabel();
optionsPanel = new javax.swing.JPanel();
jLabel6 = new javax.swing.JLabel();
delayBox = new javax.swing.JComboBox();
rangeBox = new javax.swing.JComboBox();
jLabel7 = new javax.swing.JLabel();
p1Power = new javax.swing.JToggleButton();
split = new javax.swing.JSplitPane();
chartPannel = new javax.swing.JPanel();
scroll = new javax.swing.JScrollPane();
consoleBox = new javax.swing.JTextArea();
setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);
setMinimumSize(new java.awt.Dimension(800, 180));
setName("mainFrame"); // NOI18N
setPreferredSize(new java.awt.Dimension(1052, 600));
getContentPane().setLayout(new javax.swing.BoxLayout(getContentPane(), javax.swing.BoxLayout.Y_AXIS));
valuesPanel.setBorder(javax.swing.BorderFactory.createBevelBorder(javax.swing.border.BevelBorder.RAISED));
valuesPanel.setMinimumSize(new java.awt.Dimension(0, 90));
jLabel1.setFont(new java.awt.Font("Tahoma", 0, 24)); // NOI18N
jLabel1.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
jLabel1.setText("P1");
p1Label.setFont(new java.awt.Font("Tahoma", 1, 24)); // NOI18N
p1Label.setForeground(java.awt.Color.red);
p1Label.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
p1Label.setText("EMPTY");
jLabel2.setFont(new java.awt.Font("Tahoma", 0, 24)); // NOI18N
jLabel2.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
jLabel2.setText("P2");
p2Label.setFont(new java.awt.Font("Tahoma", 1, 24)); // NOI18N
p2Label.setForeground(java.awt.Color.blue);
p2Label.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
p2Label.setText("EMPTY");
jLabel3.setFont(new java.awt.Font("Tahoma", 0, 24)); // NOI18N
jLabel3.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
jLabel3.setText("P3");
p3Label.setFont(new java.awt.Font("Tahoma", 1, 24)); // NOI18N
p3Label.setForeground(java.awt.Color.green);
p3Label.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
p3Label.setText("EMPTY");
jLabel4.setFont(new java.awt.Font("Tahoma", 0, 24)); // NOI18N
jLabel4.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
jLabel4.setText("Px");
pxLabel.setFont(new java.awt.Font("Tahoma", 1, 24)); // NOI18N
pxLabel.setForeground(java.awt.Color.magenta);
pxLabel.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
pxLabel.setText("EMPTY");
timeLabel.setFont(new java.awt.Font("Tahoma", 1, 24)); // NOI18N
timeLabel.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
timeLabel.setText("EMPTY");
jLabel5.setFont(new java.awt.Font("Tahoma", 0, 24)); // NOI18N
jLabel5.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
jLabel5.setText("time");
javax.swing.GroupLayout valuesPanelLayout = new javax.swing.GroupLayout(valuesPanel);
valuesPanel.setLayout(valuesPanelLayout);
valuesPanelLayout.setHorizontalGroup(
valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(valuesPanelLayout.createSequentialGroup()
.addGap(15, 15, 15)
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false)
.addComponent(jLabel5, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(timeLabel, javax.swing.GroupLayout.DEFAULT_SIZE, 180, Short.MAX_VALUE))
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, 122, Short.MAX_VALUE)
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false)
.addComponent(p1Label, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(jLabel1, javax.swing.GroupLayout.PREFERRED_SIZE, 81, javax.swing.GroupLayout.PREFERRED_SIZE))
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, 104, Short.MAX_VALUE)
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false)
.addComponent(p2Label, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(jLabel2, javax.swing.GroupLayout.PREFERRED_SIZE, 81, javax.swing.GroupLayout.PREFERRED_SIZE))
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, 104, Short.MAX_VALUE)
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false)
.addComponent(p3Label, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(jLabel3, javax.swing.GroupLayout.PREFERRED_SIZE, 81, javax.swing.GroupLayout.PREFERRED_SIZE))
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, 106, Short.MAX_VALUE)
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false)
.addComponent(pxLabel, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(jLabel4, javax.swing.GroupLayout.PREFERRED_SIZE, 81, javax.swing.GroupLayout.PREFERRED_SIZE))
.addContainerGap(53, Short.MAX_VALUE))
);
valuesPanelLayout.setVerticalGroup(
valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(valuesPanelLayout.createSequentialGroup()
.addContainerGap()
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(valuesPanelLayout.createSequentialGroup()
.addComponent(jLabel4)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(pxLabel))
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.TRAILING)
.addGroup(valuesPanelLayout.createSequentialGroup()
.addComponent(jLabel3)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(p3Label))
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(valuesPanelLayout.createSequentialGroup()
.addComponent(jLabel2)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(p2Label))
.addGroup(valuesPanelLayout.createSequentialGroup()
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
.addComponent(jLabel1)
.addComponent(jLabel5))
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addGroup(valuesPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
.addComponent(p1Label)
.addComponent(timeLabel))))))
.addContainerGap())
);
getContentPane().add(valuesPanel);
optionsPanel.setBorder(javax.swing.BorderFactory.createBevelBorder(javax.swing.border.BevelBorder.RAISED));
optionsPanel.setMaximumSize(new java.awt.Dimension(32767, 50));
optionsPanel.setMinimumSize(new java.awt.Dimension(0, 50));
optionsPanel.setPreferredSize(new java.awt.Dimension(1052, 50));
jLabel6.setText("Частота обновления (с):");
delayBox.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "1", "5", "10", "30", "60" }));
delayBox.setSelectedIndex(1);
delayBox.addItemListener(new java.awt.event.ItemListener() {
public void itemStateChanged(java.awt.event.ItemEvent evt) {
delayBoxItemStateChanged(evt);
}
});
rangeBox.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "10", "30", "60", "180", "300" }));
rangeBox.setSelectedIndex(2);
rangeBox.setToolTipText("");
rangeBox.addItemListener(new java.awt.event.ItemListener() {
public void itemStateChanged(java.awt.event.ItemEvent evt) {
rangeBoxItemStateChanged(evt);
}
});
rangeBox.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
rangeBoxActionPerformed(evt);
}
});
jLabel7.setText("Максимальный диапазон (мин):");
p1Power.setText("Холодный катод на P1");
p1Power.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
p1PowerActionPerformed(evt);
}
});
javax.swing.GroupLayout optionsPanelLayout = new javax.swing.GroupLayout(optionsPanel);
optionsPanel.setLayout(optionsPanelLayout);
optionsPanelLayout.setHorizontalGroup(
optionsPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(optionsPanelLayout.createSequentialGroup()
.addGap(4, 4, 4)
.addComponent(jLabel6)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
.addComponent(delayBox, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
.addGap(32, 32, 32)
.addComponent(jLabel7)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
.addComponent(rangeBox, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
.addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, 427, Short.MAX_VALUE)
.addComponent(p1Power)
.addGap(60, 60, 60))
);
optionsPanelLayout.setVerticalGroup(
optionsPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(optionsPanelLayout.createSequentialGroup()
.addContainerGap()
.addGroup(optionsPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
.addComponent(jLabel7)
.addComponent(rangeBox, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
.addComponent(delayBox, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
.addComponent(jLabel6)
.addComponent(p1Power))
.addGap(40, 40, 40))
);
getContentPane().add(optionsPanel);
split.setOrientation(javax.swing.JSplitPane.VERTICAL_SPLIT);
split.setResizeWeight(1.0);
split.setAlignmentX(0.5F);
split.setAlignmentY(0.5F);
split.setOneTouchExpandable(true);
chartPannel.setBorder(javax.swing.BorderFactory.createBevelBorder(javax.swing.border.BevelBorder.RAISED));
chartPannel.setAutoscrolls(true);
chartPannel.setLayout(new java.awt.BorderLayout());
split.setTopComponent(chartPannel);
consoleBox.setEditable(false);
consoleBox.setColumns(20);
consoleBox.setLineWrap(true);
consoleBox.setRows(5);
scroll.setViewportView(consoleBox);
consoleBox.getAccessibleContext().setAccessibleParent(split);
split.setBottomComponent(scroll);
getContentPane().add(split);
getAccessibleContext().setAccessibleParent(this);
pack();
}// </editor-fold>//GEN-END:initComponents
private void delayBoxItemStateChanged(java.awt.event.ItemEvent evt) {//GEN-FIRST:event_delayBoxItemStateChanged
setTimerInterval(Integer.parseInt((String) evt.getItem()));
}//GEN-LAST:event_delayBoxItemStateChanged
private void rangeBoxItemStateChanged(java.awt.event.ItemEvent evt) {//GEN-FIRST:event_rangeBoxItemStateChanged
setAutoRange(Integer.parseInt((String) evt.getItem()) * 60);
}//GEN-LAST:event_rangeBoxItemStateChanged
private void p1PowerActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_p1PowerActionPerformed
AbstractButton abstractButton = (AbstractButton) evt.getSource();
daemon.stop();
boolean selected = abstractButton.getModel().isSelected();
try {
updateP1PowerState(daemon.setP1PowerStateOn(selected));
} catch (P1ControlException ex) {
LoggerFactory.getLogger(getClass()).error(ex.getMessage());
try {
updateP1PowerState(daemon.getP1PowerState());
} catch (P1ControlException ex1) {
LoggerFactory.getLogger(getClass()).error(ex1.getMessage());
}
}
daemon.start();
}//GEN-LAST:event_p1PowerActionPerformed
private void rangeBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_rangeBoxActionPerformed
// TODO add your handling code here:
}//GEN-LAST:event_rangeBoxActionPerformed
private void updateP1PowerState(boolean state) {
p1Power.setSelected(state);
if (state) {
p1Power.setText("P1 включен");
} else {
p1Power.setText("P1 выключен");
}
}
public void setTimerInterval(int seconds) {
daemon.setTimerInterval(seconds * 1000);
}
public void setAutoRange(int seconds) {
plottables.setMaxAge(seconds * 1000);
}
private void displayChart() {
SwingUtilities.invokeLater(() -> {
Meta plotConfig = new MetaBuilder("plotFrame")
.setNode(new MetaBuilder("yAxis")
.setValue("logAxis", true)
.setValue("axisTitle", "pressure")
.setValue("axisUnits", "mbar")
)
.setValue("xAxis.timeAxis", true);
this.plotFrame = new JFreeChartFrame(plotConfig).display(chartPannel);
XYPlot xyPlot = plotFrame.getChart().getXYPlot();
LogarithmicAxis logAxis = new LogarithmicAxis("Pressure (mbar)");
// logAxis.setTickUnit(new NumberTickUnit(2));
logAxis.setMinorTickCount(10);
logAxis.setExpTickLabelsFlag(true);
logAxis.setMinorTickMarksVisible(true);
xyPlot.setRangeAxis(logAxis);
// xyPlot.getRenderer().setBaseStroke(new BasicStroke(3));
// xyPlot.setBackgroundPaint(Color.WHITE);
// xyPlot.setRangeGridlinesVisible(true);
// xyPlot.setRangeGridlinePaint(Color.BLACK);
//
// xyPlot.setRangeMinorGridlinesVisible(true);
// xyPlot.setRangeMinorGridlinePaint(Color.BLACK);
//adding data to the frame
plotFrame.addAll(plottables);
});
validate();
// pack();
}
private void setMaxAge(int seconds) {
plottables.setMaxAge(seconds * 1000);
}
public void displayPoint(DataPoint point) {
SwingUtilities.invokeLater(() -> {
plottables.put(point);
timeLabel.setText(formatter
.format(LocalDateTime
.ofInstant(point.getValue("timestamp").timeValue(), ZoneId.of("UTC"))));
p1Label.setText(normalize(point.getValue("P1")));
p2Label.setText(normalize(point.getValue("P2")));
p3Label.setText(normalize(point.getValue("P3")));
pxLabel.setText(normalize(point.getValue("Px")));
});
}
private String normalize(Value val) {
if (val.valueType() == ValueType.NUMBER) {
return String.format("%.2e", val.doubleValue());
} else {
return String.format("%s", val.stringValue());
}
}
// Variables declaration - do not modify//GEN-BEGIN:variables
private javax.swing.JPanel chartPannel;
private javax.swing.JTextArea consoleBox;
private javax.swing.JComboBox delayBox;
private javax.swing.JLabel jLabel1;
private javax.swing.JLabel jLabel2;
private javax.swing.JLabel jLabel3;
private javax.swing.JLabel jLabel4;
private javax.swing.JLabel jLabel5;
private javax.swing.JLabel jLabel6;
private javax.swing.JLabel jLabel7;
private javax.swing.JPanel optionsPanel;
private javax.swing.JLabel p1Label;
private javax.swing.JToggleButton p1Power;
private javax.swing.JLabel p2Label;
private javax.swing.JLabel p3Label;
private javax.swing.JLabel pxLabel;
private javax.swing.JComboBox rangeBox;
private javax.swing.JScrollPane scroll;
private javax.swing.JSplitPane split;
private javax.swing.JLabel timeLabel;
private javax.swing.JPanel valuesPanel;
// End of variables declaration//GEN-END:variables
private class JTextAreaAppender extends AppenderBase<ILoggingEvent> {
private Encoder<ILoggingEvent> encoder = new EchoEncoder<ILoggingEvent>();
private ByteArrayOutputStream out = new ByteArrayOutputStream();
private JTextArea textArea;
public JTextAreaAppender(JTextArea textArea) {
this.textArea = textArea;
}
@Override
public void start() {
try {
encoder.init(out);
} catch (IOException e) {
}
super.start();
}
@Override
public void append(ILoggingEvent event) {
try {
encoder.doEncode(event);
out.flush();
String line = out.toString();
textArea.append(line);
out.reset();
} catch (IOException e) {
}
}
}
}

View File

@ -1,223 +0,0 @@
/*
* Copyright 2015 Alexander Nozik.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package inr.numass.readvac;
import hep.dataforge.exceptions.StorageException;
import hep.dataforge.meta.Meta;
import hep.dataforge.storage.api.PointLoader;
import hep.dataforge.storage.api.Storage;
import hep.dataforge.storage.commons.LoaderFactory;
import hep.dataforge.tables.DataPoint;
import hep.dataforge.tables.TableFormatBuilder;
import hep.dataforge.values.ValueType;
import java.time.Instant;
import java.util.Iterator;
import java.util.Timer;
import java.util.TimerTask;
import javax.swing.SwingUtilities;
import jssc.SerialPortException;
import org.slf4j.LoggerFactory;
/**
*
* @author Darksnake
*/
public class VACManager implements AutoCloseable {
public static String[] names = {"timestamp", "P1", "P2", "P3", "Px"};
private VACFrame frame;
private Timer timer;
private int timerInterval = 5000;
// private boolean isValuesShowing;
// private boolean isLogShowing;
private final PointLoader loader;
private VACDeviceReader device;
private final Iterator<DataPoint> reader; // Чтение из файла или непосредтсвенно с прибора
private Instant lastUpdate;
// public static VACManager fromDirectory(Storage server, String sourceDir, String runPrefix) throws StorageException, FileNotFoundException {
// return new VACManager(setupLoader(server, runPrefix), VACFileReader.fromDirectory(sourceDir));
// }
public static VACManager fromSerial(Storage server, String run, Meta serialConfig) throws StorageException, SerialPortException {
return new VACManager(setupLoader(server, run), new VACDeviceReader(serialConfig));
}
public VACManager(PointLoader loader, Iterator<DataPoint> reader) {
this.loader = loader;
this.reader = reader;
showPlot();
}
public VACManager(PointLoader loader, VACDeviceReader reader) {
this.loader = loader;
this.reader = reader;
this.device = reader;
showPlot();
}
private static PointLoader setupLoader(Storage storage, String run) throws StorageException {
return LoaderFactory.buildPointLoder(storage, "vactms", run, "timestamp",
new TableFormatBuilder(names)
.setType("timestamp", ValueType.TIME)
.build());
}
/**
* @return the timerInterval
*/
public int getTimerInterval() {
return timerInterval;
}
/**
* Интервал в милисекундах
*
* @param millis
*/
public void setTimerInterval(int millis) {
this.timerInterval = millis;
//Перезапускаем таймер, чтобы обновились интервалы
stop();
start();
// setAutoRange(millis*500);
}
public void start() {
timer = new Timer("UpdateTimer");
timer.scheduleAtFixedRate(getTimerTask(), 0, getTimerInterval());
}
public void stop() {
timer.cancel();
}
@Override
public void close() throws Exception {
stop();
if (device != null) {
device.close();
}
loader.close();
}
public final void showPlot() {
if (frame != null) {
if (frame.isDisplayable()) {
frame.setVisible(true);
} else {
//Подчищаем неправильно закрытые окна
frame.dispose();
frame = null;
}
}
if (frame == null) {
SwingUtilities.invokeLater(() -> {
frame = VACFrame.display(VACManager.this);
});
}
}
public DataPoint readPoint() {
return reader.next();
}
public boolean hasNextPoint() {
return reader.hasNext();
}
/**
* Пропускаем все точки, до определенного момента. Возвращаем последнюю
* точку в списке, или первую, время которой больше, чем у заданной
*
* @param time
* @return
*/
public DataPoint skipUntil(Instant time) {
if (reader.hasNext()) {
DataPoint point = reader.next();
while (point.getValue("timestamp").timeValue().isBefore(time) && reader.hasNext()) {
point = reader.next();
}
return point;
} else {
return null;
}
}
public boolean p1Available() {
return (device != null) && (device.isP1Available());
}
public boolean getP1PowerState() throws P1ControlException {
try {
if (device == null) {
throw new P1ControlException("P1 control is not initialized");
}
return device.getP1PowerState();
} catch (SerialPortException | ResponseParseException ex) {
throw new P1ControlException("Can't read P1 answer");
}
}
public boolean setP1PowerStateOn(boolean state) throws P1ControlException {
try {
if (device == null) {
throw new P1ControlException("P1 control is not initialized");
}
return device.setP1PowerStateOn(state);
} catch (SerialPortException | ResponseParseException ex) {
throw new P1ControlException("Can't read P1 answer");
}
}
private TimerTask getTimerTask() {
return new TimerTask() {
@Override
public void run() {
try {
// while (hasNextPoint()) {
if (hasNextPoint()) {
DataPoint point = readPoint();
// На всякий случай берем время на секунду назад, чтобы не было накладок с пропусками
// DataPoint point = skipUntil(Instant.now().minusSeconds(1));
//Проверяем, что точка получена
if (point != null) {
//Если точка старая, то не обновляем ничего
Instant pointTime = point.getValue("timestamp").timeValue();
if (lastUpdate != null && pointTime.isAfter(lastUpdate)) {
loader.push(point);
if (frame != null) {
frame.displayPoint(point);
}
}
lastUpdate = pointTime;
}
}
} catch (Exception ex) {
LoggerFactory.getLogger(VACManager.class).error("Unexpected error during point aquisition", ex);
}
}
};
}
}

View File

@ -17,7 +17,7 @@ File dataDir = new File("D:\\Work\\Numass\\data\\2016_04\\T2_data\\Fill_1_7\\set
if(!dataDir.exists()){
println "dataDir directory does not exist"
}
Meta config = new GrindMetaBuilder().config(lower: 500, upper: 1600)
Meta config = new GrindMetaBuilder().config(lower: 500, upper: 1800)
println config
NumassData data = NumassDataLoader.fromLocalDir(null, dataDir)
new FindBorderAction().eval(data, config)

View File

@ -37,7 +37,6 @@ import inr.numass.actions.PrepareDataAction;
import inr.numass.actions.ReadNumassDataAction;
import inr.numass.actions.ReadNumassStorageAction;
import inr.numass.actions.ShowLossSpectrumAction;
import inr.numass.actions.ShowSpectrumAction;
import inr.numass.actions.SlicingAction;
import inr.numass.actions.SummaryAction;
import inr.numass.models.BetaSpectrum;
@ -73,7 +72,6 @@ public class NumassPlugin extends BasicPlugin {
ActionManager actions = ActionManager.buildFrom(context);
actions.registerAction(SlicingAction.class);
actions.registerAction(ShowSpectrumAction.class);
actions.registerAction(PrepareDataAction.class);
actions.registerAction(ReadNumassDataAction.class);
actions.registerAction(MergeDataAction.class);

View File

@ -1,168 +0,0 @@
/*
* Copyright 2015 Alexander Nozik.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package inr.numass.actions;
import hep.dataforge.actions.OneToOneAction;
import hep.dataforge.context.Context;
import hep.dataforge.description.TypedActionDef;
import hep.dataforge.exceptions.ContentException;
import hep.dataforge.io.ColumnedDataWriter;
import hep.dataforge.io.reports.Reportable;
import hep.dataforge.meta.Laminate;
import hep.dataforge.meta.Meta;
import hep.dataforge.plots.fx.FXPlotUtils;
import hep.dataforge.plots.jfreechart.JFreeChartFrame;
import inr.numass.data.ESpectrum;
import inr.numass.storage.NMFile;
import inr.numass.storage.NMPoint;
import java.awt.Color;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.renderer.xy.XYLineAndShapeRenderer;
import org.jfree.data.xy.XYSeries;
import org.jfree.data.xy.XYSeriesCollection;
import org.jfree.ui.RectangleEdge;
/**
*
* @author Darksnake
*/
@TypedActionDef(name = "showSpectrum", inputType = NMFile.class, outputType = NMFile.class)
public class ShowSpectrumAction extends OneToOneAction<NMFile, NMFile> {
@Override
protected NMFile execute(Context context, Reportable log, String name, Laminate meta, NMFile source) throws ContentException {
log.report("File {} started", source.getName());
List<NMPoint> printPoints = new ArrayList<>();
List<NMPoint> showPoints = new ArrayList<>();
for (NMPoint point : source.getNMPoints()) {
if (toPrint(point, meta)) {
printPoints.add(point);
}
if (toShow(point, meta)) {
showPoints.add(point);
}
}
int chanelsPerBin = meta.getInt("binning", 1); // биннинг
boolean normalize = meta.getBoolean("normalize", false); // нормировка на время набора точки
if (showPoints.size() > 0) {
showSpectra(showPoints, source.getName(), chanelsPerBin, normalize);
}
if (printPoints.size() > 0) {
ESpectrum data = new ESpectrum(printPoints, chanelsPerBin, normalize);
OutputStream stream = buildActionOutput(context, name);
ColumnedDataWriter.writeDataSet(stream, data, source.getName());
}
log.report("File {} completed", source.getName());
return source;
}
private boolean toPrint(NMPoint point, Meta meta) throws ContentException {
if (meta.hasNode("print")) {
List<? extends Meta> cfg = meta.getNodes("print");
boolean res = false;
for (Meta e : cfg) {
double from = e.getDouble("from", 0);
double to = e.getDouble("to", Double.POSITIVE_INFINITY);
res = res || ((point.getUset() >= from) && (point.getUset() <= to));
}
return res;
} else {
return meta.getBoolean("print", false);
}
}
private boolean toShow(NMPoint point, Meta meta) throws ContentException {
if (meta.hasNode("show")) {
List<? extends Meta> cfg = meta.getNodes("show");
boolean res = false;
for (Meta e : cfg) {
double from = e.getDouble("from", 0);
double to = e.getDouble("to", Double.POSITIVE_INFINITY);
res = res || ((point.getUset() >= from) && (point.getUset() <= to));
}
return res;
} else {
return meta.getBoolean("show", false);
}
}
private static void showSpectra(List<NMPoint> points, String head, int binning, boolean normalize) {
XYSeriesCollection dataset = new XYSeriesCollection();
for (NMPoint point : points) {
Map<Double, Double> spectrum = point.getMapWithBinning(binning, normalize);
String serName = Double.toString(point.getUset());
XYSeries ser;
if (dataset.getSeriesIndex(serName) >= 0) {
serName = serName + " " + Integer.toString(points.indexOf(point));
}
ser = new XYSeries(serName);
for (Map.Entry<Double, Double> sp : spectrum.entrySet()) {
ser.add(sp.getKey(), sp.getValue());
}
dataset.addSeries(ser);
}
showSpectra(dataset, head, binning, normalize);
}
private static void showSpectra(XYSeriesCollection dataset, String head, int binning, boolean normalize) {
String axisName = "count";
if (normalize) {
axisName += " rate";
} else {
axisName += " number";
}
if (binning != 1) {
axisName += " per " + binning + " chanels";
}
JFreeChartFrame frame = FXPlotUtils.displayJFreeChart(head, null);
frame.getYAxisConfig().putValue("title", axisName);
JFreeChart chart = frame.getChart();
chart.getXYPlot().setDataset(dataset);
chart.getXYPlot().setRenderer(new XYLineAndShapeRenderer(true, false));
chart.getLegend().setPosition(RectangleEdge.RIGHT);
chart.getXYPlot().setDomainGridlinesVisible(true);
chart.getXYPlot().setRangeGridlinesVisible(true);
chart.getXYPlot().setDomainGridlinePaint(Color.BLACK);
chart.getXYPlot().setRangeGridlinePaint(Color.BLACK);
}
}

View File

@ -239,11 +239,9 @@ public class NumassWorkbenchController implements Initializable, StagePaneHolder
for (Configuration action : actions) {
counter++;
MetaEditor actionEditor = new MetaEditor();
MetaTreeItem rootItem = new MetaTreeItem(action, getDescriptorForAction(action.getString("type")));
//Freezing actions names
// rootItem.setFrozenValuePredicate((c, n) -> c.getName().equals("action") && n.equals("type"));
actionEditor.setRoot(rootItem);
actionEditor.setRoot(action, getDescriptorForAction(action.getString("type")));
actionEditors.add(actionEditor);
String actionTitle = String.format("action [%d]: %s", counter, action.getString("type"));

View File

@ -20,7 +20,7 @@ public class PlotOutputTab extends OutputTab {
container.setPlot(frame);
// AnchorPane pane = new AnchorPane();
// frame = new JFreeChartFrame(name, meta).display(pane);
setContent(container);
setContent(container.getRoot());
}
public PlotOutputTab(String name, String title, Meta meta) {
@ -28,7 +28,7 @@ public class PlotOutputTab extends OutputTab {
PlotContainer container = new PlotContainer();
frame = new JFreeChartFrame(meta);
container.setPlot(frame);
setContent(container);
setContent(container.getRoot());
}
@Override

View File

@ -30,6 +30,7 @@ import hep.dataforge.plots.XYPlottable;
import hep.dataforge.plots.data.ChangeablePlottableData;
import hep.dataforge.plots.data.PlotDataUtils;
import hep.dataforge.plots.data.PlottableData;
import hep.dataforge.plots.fx.PlotContainer;
import hep.dataforge.plots.jfreechart.JFreeChartFrame;
import hep.dataforge.storage.commons.JSONMetaWriter;
import hep.dataforge.tables.DataPoint;
@ -48,7 +49,6 @@ import java.util.ResourceBundle;
import java.util.function.Predicate;
import java.util.stream.Collectors;
import javafx.application.Platform;
import javafx.beans.property.BooleanProperty;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.collections.FXCollections;
@ -57,10 +57,13 @@ import javafx.event.ActionEvent;
import javafx.fxml.FXML;
import javafx.fxml.FXMLLoader;
import javafx.fxml.Initializable;
import javafx.geometry.Insets;
import javafx.geometry.Orientation;
import javafx.scene.control.Button;
import javafx.scene.control.CheckBox;
import javafx.scene.control.ChoiceBox;
import javafx.scene.control.SelectionMode;
import javafx.scene.control.Label;
import javafx.scene.control.Separator;
import javafx.scene.control.Tab;
import javafx.scene.control.TextArea;
import javafx.scene.control.TextField;
@ -86,10 +89,13 @@ public class NumassLoaderViewComponent extends AnchorPane implements Initializab
Logger logger = LoggerFactory.getLogger(NumassLoaderViewComponent.class);
private NumassData data;
private XYPlotFrame detectorPlotFrame;
private PlotContainer detectorPlot;
private XYPlotFrame spectrumPlotFrame;
private ChangeablePlottableData spectrumData;
private List<NMPoint> points;
private ChoiceBox<Integer> detectorBinningSelector;
private CheckBox detectorNormalizeSwitch;
private Button detectorDataExportButton;
@FXML
private AnchorPane detectorPlotPane;
@ -104,18 +110,10 @@ public class NumassLoaderViewComponent extends AnchorPane implements Initializab
@FXML
private TextArea infoTextBox;
@FXML
private VBox detectorOptionsPane;
@FXML
private AnchorPane spectrumPlotPane;
@FXML
private VBox spectrumOptionsPane;
@FXML
private ChoiceBox<Integer> detectorBinningSelector;
@FXML
private CheckBox detectorNormalizeSwitch;
@FXML
private Button detectorDataExportButton;
@FXML
private TextField lowChannelField;
@FXML
private TextField upChannelField;
@ -148,12 +146,28 @@ public class NumassLoaderViewComponent extends AnchorPane implements Initializab
*/
@Override
public void initialize(URL url, ResourceBundle rb) {
detectorBinningSelector.setItems(FXCollections.observableArrayList(1, 2, 5, 10, 20, 50));
//setup detector pane plot and sidebar
Label l = new Label("Bin size:");
l.setPadding(new Insets(5));
detectorBinningSelector = new ChoiceBox<>(FXCollections.observableArrayList(1, 2, 5, 10, 20, 50));
detectorBinningSelector.setMaxWidth(Double.MAX_VALUE);
detectorBinningSelector.getSelectionModel().select(4);
detectorNormalizeSwitch.setSelected(true);
detectorPointListView.getSelectionModel().setSelectionMode(SelectionMode.MULTIPLE);
detectorNormalizeSwitch = new CheckBox("Normailize");
detectorNormalizeSwitch.setSelected(true);
detectorNormalizeSwitch.setPadding(new Insets(5));
detectorPlot = PlotContainer.anchorTo(detectorPlotPane);
detectorPlot.addToSideBar(0, l, detectorBinningSelector, detectorNormalizeSwitch, new Separator(Orientation.HORIZONTAL));
detectorDataExportButton = new Button("Export");
detectorDataExportButton.setMaxWidth(Double.MAX_VALUE);
detectorDataExportButton.setOnAction(this::onExportButtonClick);
detectorPlot.addToSideBar(detectorDataExportButton);
detectorPlot.setSideBarPosition(0.7);
//setup spectrum pane
lowChannelField.textProperty().bindBidirectional(channelSlider.lowValueProperty(), new NumberStringConverter());
upChannelField.textProperty().bindBidirectional(channelSlider.highValueProperty(), new NumberStringConverter());
@ -202,16 +216,6 @@ public class NumassLoaderViewComponent extends AnchorPane implements Initializab
setupInfo(data);
});
});
// LoadPointsTask task = new LoadPointsTask(data);
// if (callback != null) {
// callback.postTask(task);
// }
// Viewer.runTask(task);
// try {
// this.points = task.getRow();
// } catch (InterruptedException | ExecutionException ex) {
// logger.error("Can't load spectrum data points", ex);
// }
} else {
logger.error("The data model is null");
}
@ -280,7 +284,7 @@ public class NumassLoaderViewComponent extends AnchorPane implements Initializab
.setValue("legend.show", false);
spectrumPlotFrame = new JFreeChartFrame(plotMeta).display(spectrumPlotPane);
}
if (spectrumData == null) {
@ -323,9 +327,8 @@ public class NumassLoaderViewComponent extends AnchorPane implements Initializab
throw new IllegalArgumentException("Detector data not defined");
}
detectorPointListView.getItems().clear();//removing all checkboxes
detectorPlotPane.getChildren().clear();//removing plot
// detectorPointListView.getItems().clear();//removing all checkboxes
// detectorPlotPane.getChildren().clear();//removing plot
Meta frameMeta = new MetaBuilder("frame")
.setValue("frameTitle", "Detector response plot")
.setNode(new MetaBuilder("xAxis")
@ -336,23 +339,18 @@ public class NumassLoaderViewComponent extends AnchorPane implements Initializab
.setValue("axisTitle", "count rate")
.setValue("axisUnits", "Hz")
.build())
.setNode(new MetaBuilder("legend")
.setValue("show", false))
.build();
detectorPlotFrame = new JFreeChartFrame(frameMeta).display(detectorPlotPane);
// detectorPlot = PlotContainer.anchorTo(detectorPlotPane);
XYPlotFrame detectorPlotFrame = new JFreeChartFrame(frameMeta);
for (XYPlottable pl : detectorData) {
detectorPlotFrame.add(pl);
detectorPointListView.getItems().add(pl.getName());
}
for (String plotName : detectorPointListView.getItems()) {
BooleanProperty checked = detectorPointListView.getItemBooleanProperty(plotName);
checked.set(true);
checked.addListener((ObservableValue<? extends Boolean> observable, Boolean oldValue, Boolean newValue) -> {
detectorPlotFrame.get(plotName).getConfig().setValue("visible", newValue);
});
//TODO add update instead of replace action
}
detectorPlot.setPlot(detectorPlotFrame);
});
}
@ -449,7 +447,7 @@ public class NumassLoaderViewComponent extends AnchorPane implements Initializab
fileChooser.setInitialFileName(data.getName() + "_detector.out");
File destination = fileChooser.showSaveDialog(detectorPlotPane.getScene().getWindow());
if (destination != null) {
Table detectorData = PlotDataUtils.collectXYDataFromPlot(detectorPlotFrame, true);
Table detectorData = PlotDataUtils.collectXYDataFromPlot((XYPlotFrame) detectorPlot.getPlot(), true);
try {
ColumnedDataWriter
.writeDataSet(destination, detectorData, "Numass data viewer detector data export for " + data.getName(),

View File

@ -16,120 +16,92 @@ See the License for the specific language governing permissions and
limitations under the License.
-->
<?import org.controlsfx.control.textfield.*?>
<?import org.controlsfx.control.*?>
<?import javafx.geometry.*?>
<?import java.lang.*?>
<?import java.util.*?>
<?import javafx.scene.*?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>
<?import javafx.geometry.Insets?>
<?import javafx.scene.control.Button?>
<?import javafx.scene.control.Label?>
<?import javafx.scene.control.Separator?>
<?import javafx.scene.control.Tab?>
<?import javafx.scene.control.TabPane?>
<?import javafx.scene.control.TextArea?>
<?import javafx.scene.control.TextField?>
<?import javafx.scene.control.ToolBar?>
<?import javafx.scene.layout.AnchorPane?>
<?import javafx.scene.layout.BorderPane?>
<?import javafx.scene.layout.HBox?>
<?import javafx.scene.layout.Pane?>
<?import javafx.scene.layout.VBox?>
<?import org.controlsfx.control.RangeSlider?>
<fx:root id="AnchorPane" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" type="AnchorPane" xmlns="http://javafx.com/javafx/8.0.40" xmlns:fx="http://javafx.com/fxml/1">
<children>
<TabPane layoutX="200.0" layoutY="100.0" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" tabClosingPolicy="UNAVAILABLE" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0">
<tabs>
<Tab text="Info">
<content>
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0">
<children>
<TextArea fx:id="infoTextBox" layoutY="30.0" prefHeight="200.0" prefWidth="200.0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="30.0" />
</children>
</AnchorPane>
</content>
</Tab>
<Tab fx:id="detectorTab" text="Detector">
<content>
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0">
<children>
<SplitPane dividerPositions="0.5" prefHeight="200.0" prefWidth="200.0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0">
<items>
<AnchorPane fx:id="detectorPlotPane" minHeight="300.0" minWidth="300.0" prefHeight="200.0" prefWidth="200.0" />
<VBox fx:id="detectorOptionsPane" maxWidth="250.0" prefWidth="200.0" spacing="2.0" style="-fx-border-color: blue;">
<children>
<Label text="Channels per bin">
<VBox.margin>
<Insets left="5.0" right="5.0" />
</VBox.margin>
</Label>
<ChoiceBox fx:id="detectorBinningSelector" prefWidth="150.0" />
<CheckBox fx:id="detectorNormalizeSwitch" mnemonicParsing="false" text="Normalize">
<VBox.margin>
<Insets bottom="5.0" left="5.0" right="5.0" top="5.0" />
</VBox.margin>
</CheckBox>
<CheckListView fx:id="detectorPointListView" VBox.vgrow="ALWAYS">
<contextMenu>
<ContextMenu>
<fx:root id="AnchorPane" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" type="AnchorPane" xmlns="http://javafx.com/javafx/8.0.65" xmlns:fx="http://javafx.com/fxml/1">
<children>
<TabPane layoutX="200.0" layoutY="100.0" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" tabClosingPolicy="UNAVAILABLE" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0">
<tabs>
<Tab text="Info">
<content>
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0">
<children>
<TextArea fx:id="infoTextBox" layoutY="30.0" prefHeight="200.0" prefWidth="200.0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="30.0" />
</children>
</AnchorPane>
</content>
</Tab>
<Tab fx:id="detectorTab" text="Detector">
<content>
<AnchorPane fx:id="detectorPlotPane" minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0" />
</content>
</Tab>
<Tab fx:id="hvTab" text="HV">
<content>
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0" />
</content>
</Tab>
<Tab fx:id="spectrumTab" text="Spectrum">
<content>
<AnchorPane minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0">
<children>
<BorderPane prefHeight="200.0" prefWidth="200.0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0">
<center>
<AnchorPane fx:id="spectrumPlotPane" prefHeight="200.0" prefWidth="200.0" BorderPane.alignment="CENTER" />
</center>
<top>
<ToolBar prefHeight="40.0" prefWidth="200.0" BorderPane.alignment="CENTER">
<items>
<MenuItem mnemonicParsing="false" onAction="#checkAllAction" text="Check all" />
<MenuItem mnemonicParsing="false" onAction="#uncheckAllAction" text="Uncheck all" />
<MenuItem mnemonicParsing="false" onAction="#checkSelectedAction" text="Check selected" />
<MenuItem mnemonicParsing="false" onAction="#uncheckSelectedAction" text="Uncheck selected" />
<VBox>
<children>
<Label text="Lo channel" />
<TextField fx:id="lowChannelField" prefWidth="60.0" />
</children>
</VBox>
<RangeSlider fx:id="channelSlider" accessibleRole="SLIDER" highValue="1900.0" lowValue="300.0" majorTickUnit="500.0" max="4000.0" minorTickCount="5" prefHeight="38.0" prefWidth="276.0" showTickLabels="true" showTickMarks="true">
<padding>
<Insets left="10.0" right="10.0" />
</padding>
</RangeSlider>
<VBox>
<children>
<Label text="Up channel" />
<TextField fx:id="upChannelField" prefWidth="60.0" />
</children>
</VBox>
<Separator orientation="VERTICAL" />
<VBox>
<children>
<Label text="Dead time (us)" />
<TextField fx:id="dTimeField" prefHeight="25.0" prefWidth="0.0" text="7.2" />
</children>
</VBox>
<Separator orientation="VERTICAL" />
<Pane minWidth="0.0" HBox.hgrow="ALWAYS" />
<Button fx:id="spectrumExportButton" mnemonicParsing="false" onAction="#onSpectrumExportClick" text="Export" />
</items>
</ContextMenu>
</contextMenu></CheckListView>
<Button fx:id="detectorDataExportButton" alignment="CENTER" disable="true" mnemonicParsing="false" prefWidth="500.0" text="Export" />
</children>
<padding>
<Insets bottom="2.0" left="2.0" right="2.0" top="2.0" />
</padding></VBox>
</items>
</SplitPane>
</children>
</AnchorPane>
</content>
</Tab>
<Tab fx:id="hvTab" text="HV">
<content>
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0" />
</content>
</Tab>
<Tab fx:id="spectrumTab" text="Spectrum">
<content>
<AnchorPane minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0">
<children>
<BorderPane prefHeight="200.0" prefWidth="200.0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0">
<center>
<AnchorPane fx:id="spectrumPlotPane" prefHeight="200.0" prefWidth="200.0" BorderPane.alignment="CENTER" />
</center>
<top>
<ToolBar prefHeight="40.0" prefWidth="200.0" BorderPane.alignment="CENTER">
<items>
<VBox>
<children>
<Label text="Lo channel" />
<TextField fx:id="lowChannelField" prefWidth="60.0" />
</children>
</VBox>
<RangeSlider fx:id="channelSlider" accessibleRole="SLIDER" highValue="1900.0" lowValue="300.0" majorTickUnit="500.0" max="4000.0" minorTickCount="5" prefHeight="38.0" prefWidth="276.0" showTickLabels="true" showTickMarks="true">
<padding>
<Insets left="10.0" right="10.0" />
</padding></RangeSlider>
<VBox>
<children>
<Label text="Up channel" />
<TextField fx:id="upChannelField" prefWidth="60.0" />
</children>
</VBox>
<Separator orientation="VERTICAL" />
<VBox>
<children>
<Label text="Dead time (us)" />
<TextField fx:id="dTimeField" prefHeight="25.0" prefWidth="0.0" text="7.2" />
</children>
</VBox>
<Separator orientation="VERTICAL" />
<Pane minWidth="0.0" HBox.hgrow="ALWAYS" />
<Button fx:id="spectrumExportButton" mnemonicParsing="false" onAction="#onSpectrumExportClick" text="Export" />
</items>
</ToolBar>
</top>
</BorderPane>
</children></AnchorPane>
</content>
</Tab>
</tabs>
</TabPane>
</children>
</ToolBar>
</top>
</BorderPane>
</children>
</AnchorPane>
</content>
</Tab>
</tabs>
</TabPane>
</children>
</fx:root>