Skip to content

Commit 3773f7e

Browse files
committed
Initial version
Adds IOPlugin for writing Tables to CSV files. This is a very basic version of an IOPlugin that writes a Table to a CSV file with predefined settings. There are no conversions involved yet when reading from a CSV file.
0 parents  commit 3773f7e

5 files changed

Lines changed: 420 additions & 0 deletions

File tree

.gitignore

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
# Maven #
2+
/target/
3+
4+
# Eclipse #
5+
/.classpath
6+
/.project
7+
/.settings/
8+
9+
# IntelliJ #
10+
/.idea/
11+
/*.iml

README.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
ImageJ IO Plugins: Table
2+
------------------------
3+
4+
I/O plugins for ImageJ `Table` objects.

pom.xml

Lines changed: 116 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
3+
<modelVersion>4.0.0</modelVersion>
4+
5+
<parent>
6+
<groupId>org.scijava</groupId>
7+
<artifactId>pom-scijava</artifactId>
8+
<version>17.2.0</version>
9+
<relativePath />
10+
</parent>
11+
12+
<groupId>net.imagej</groupId>
13+
<artifactId>imagej-plugins-io-table</artifactId>
14+
<version>0.0.1-SNAPSHOT</version>
15+
16+
<name>ImageJ IO Plugin: Tables</name>
17+
<description>I/O plugins for ImageJ table objects</description>
18+
<url>https://imagej.net/ImageJ_Plugins_IO_Table</url>
19+
<inceptionYear>2017</inceptionYear>
20+
<organization>
21+
<name>ImageJ</name>
22+
<url>https://imagej.net</url>
23+
</organization>
24+
<licenses>
25+
<license>
26+
<name>Simplified BSD License</name>
27+
<distribution>repo</distribution>
28+
</license>
29+
</licenses>
30+
31+
<developers>
32+
<!-- See https://imagej.net/Team -->
33+
<developer>
34+
<id>stelfrich</id>
35+
<name>Stefan Helfrich</name>
36+
<url>https://imagej.net/User:stelfrich</url>
37+
<roles>
38+
<role>founder</role>
39+
<role>lead</role>
40+
<role>developer</role>
41+
<role>debugger</role>
42+
<role>reviewer</role>
43+
<role>support</role>
44+
<role>maintainer</role>
45+
</roles>
46+
</developer>
47+
</developers>
48+
49+
<contributors>
50+
<contributor>
51+
<name>Leon Yang</name>
52+
<url>http://imagej.net/User:Leon</url>
53+
<properties><id>lnyng</id></properties>
54+
</contributor>
55+
</contributors>
56+
57+
<mailingLists>
58+
<mailingList>
59+
<name>ImageJ Forum</name>
60+
<archive>http://forum.imagej.net/</archive>
61+
</mailingList>
62+
</mailingLists>
63+
64+
<scm>
65+
<connection>scm:git:git://github.com/imagej/imagej-plugins-io-table</connection>
66+
<developerConnection>scm:git:git@github.com:imagej/imagej-plugins-io-table</developerConnection>
67+
<tag>HEAD</tag>
68+
<url>https://github.com/imagej/imagej-plugins-io-table</url>
69+
</scm>
70+
<issueManagement>
71+
<system>GitHub Issues</system>
72+
<url>https://github.com/imagej/imagej-plugins-io-table/issues</url>
73+
</issueManagement>
74+
<ciManagement>
75+
<system>None</system>
76+
</ciManagement>
77+
78+
<properties>
79+
<package-name>net.imagej.table</package-name>
80+
<license.licenseName>bsd_2</license.licenseName>
81+
<license.copyrightOwners>Board of Regents of the University of
82+
Wisconsin-Madison, Broad Institute of MIT and Harvard, and Max Planck
83+
Institute of Molecular Cell Biology and Genetics.</license.copyrightOwners>
84+
<license.projectName>ImageJ software for multidimensional image processing and analysis.</license.projectName>
85+
</properties>
86+
87+
<repositories>
88+
<repository>
89+
<id>imagej.public</id>
90+
<url>http://maven.imagej.net/content/groups/public</url>
91+
</repository>
92+
</repositories>
93+
94+
<dependencies>
95+
<dependency>
96+
<groupId>net.imagej</groupId>
97+
<artifactId>imagej-common</artifactId>
98+
</dependency>
99+
<dependency>
100+
<groupId>org.scijava</groupId>
101+
<artifactId>scijava-common</artifactId>
102+
</dependency>
103+
<dependency>
104+
<groupId>org.apache.commons</groupId>
105+
<artifactId>commons-csv</artifactId>
106+
<version>1.3</version>
107+
</dependency>
108+
109+
<!-- Test scope dependencies -->
110+
<dependency>
111+
<groupId>junit</groupId>
112+
<artifactId>junit</artifactId>
113+
<scope>test</scope>
114+
</dependency>
115+
</dependencies>
116+
</project>
Lines changed: 175 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,175 @@
1+
/*
2+
* #%L
3+
* SciJava Common shared library for SciJava software.
4+
* %%
5+
* Copyright (C) 2009 - 2016 Board of Regents of the University of
6+
* Wisconsin-Madison, Broad Institute of MIT and Harvard, and Max Planck
7+
* Institute of Molecular Cell Biology and Genetics.
8+
* %%
9+
* Redistribution and use in source and binary forms, with or without
10+
* modification, are permitted provided that the following conditions are met:
11+
*
12+
* 1. Redistributions of source code must retain the above copyright notice,
13+
* this list of conditions and the following disclaimer.
14+
* 2. Redistributions in binary form must reproduce the above copyright notice,
15+
* this list of conditions and the following disclaimer in the documentation
16+
* and/or other materials provided with the distribution.
17+
*
18+
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
19+
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20+
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21+
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE
22+
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
23+
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
24+
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
25+
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
26+
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27+
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
28+
* POSSIBILITY OF SUCH DAMAGE.
29+
* #L%
30+
*/
31+
32+
package net.imagej.table;
33+
34+
import java.io.File;
35+
import java.io.FileReader;
36+
import java.io.FileWriter;
37+
import java.io.IOException;
38+
import java.util.LinkedList;
39+
import java.util.List;
40+
import java.util.Set;
41+
42+
import org.apache.commons.csv.CSVFormat;
43+
import org.apache.commons.csv.CSVParser;
44+
import org.apache.commons.csv.CSVPrinter;
45+
import org.apache.commons.csv.CSVRecord;
46+
import org.scijava.Priority;
47+
import org.scijava.io.AbstractIOPlugin;
48+
import org.scijava.io.IOPlugin;
49+
import org.scijava.log.LogService;
50+
import org.scijava.plugin.Parameter;
51+
import org.scijava.plugin.Plugin;
52+
import org.scijava.util.FileUtils;
53+
54+
/**
55+
* {@link IOPlugin} for writing {@link Table}s to csv.
56+
*
57+
* @author Stefan Helfrich
58+
*/
59+
@SuppressWarnings("rawtypes")
60+
@Plugin(type = IOPlugin.class, priority = Priority.LOW_PRIORITY - 1)
61+
public class TableIOPlugin extends AbstractIOPlugin<Table> {
62+
63+
@Parameter
64+
private LogService log;
65+
66+
/** Delimiter used in CSV file */
67+
@Parameter(required = false)
68+
private char delimiter = '\t';
69+
70+
/** Quote character used in CSV file */
71+
@Parameter(required = false)
72+
private char quote = '"';
73+
74+
/** Line separator used in CSV file */
75+
@Parameter(required = false)
76+
private String recordSeparator = "\r\n";
77+
78+
// -- IOPlugin methods --
79+
80+
@Override
81+
public Class<Table> getDataType() {
82+
return Table.class;
83+
}
84+
85+
@Override
86+
public boolean supportsOpen(final String source) {
87+
File file = new File(source);
88+
return FileUtils.getExtension(file).equalsIgnoreCase("csv");
89+
}
90+
91+
@SuppressWarnings("unchecked")
92+
@Override
93+
public Table open(final String source) throws IOException {
94+
// Create the CSVFormat object
95+
CSVFormat csvFileFormat = CSVFormat.DEFAULT.withHeader()
96+
.withIgnoreEmptyLines(true).withDelimiter(delimiter).withQuote(quote)
97+
.withRecordSeparator(recordSeparator);
98+
99+
// Create a table
100+
Table table = new DefaultGenericTable();
101+
102+
// Initialize FileReader and CSVParser in try-with-resource
103+
try (FileReader fileReader = new FileReader(new File(source));
104+
CSVParser csvFileParser = new CSVParser(fileReader, csvFileFormat);)
105+
{
106+
// Read headers
107+
Set<String> keySet = csvFileParser.getHeaderMap().keySet();
108+
String[] headers = new String[keySet.size()];
109+
keySet.toArray(headers);
110+
111+
// Get a list of CSV file records
112+
List<CSVRecord> csvRecords = csvFileParser.getRecords();
113+
114+
// Create columns and rows
115+
table.appendColumns(headers);
116+
table.appendRows(csvRecords.size());
117+
118+
// Read the CSV file
119+
int counter = 0;
120+
for (CSVRecord record : csvRecords) {
121+
for (String columnHeader : headers) {
122+
table.set(columnHeader, counter, record.get(columnHeader));
123+
}
124+
125+
counter++;
126+
}
127+
}
128+
catch (Exception e) {
129+
log.error(e);
130+
}
131+
132+
return table;
133+
}
134+
135+
@Override
136+
public void save(Table data, String destination) throws IOException {
137+
// Create the CSVFormat object
138+
CSVFormat csvFileFormat = CSVFormat.DEFAULT.withIgnoreEmptyLines(true)
139+
.withDelimiter(delimiter).withQuote(quote).withRecordSeparator(
140+
recordSeparator);
141+
142+
// Initialize FileWriter and CSVPrinter in try-with-resource
143+
try (FileWriter fileWriter = new FileWriter(destination);
144+
CSVPrinter csvFilePrinter = new CSVPrinter(fileWriter, csvFileFormat))
145+
{
146+
// Get column headers from table
147+
List<String> headers = new LinkedList<>();
148+
for (int col = 0; col < data.getColumnCount(); ++col) {
149+
headers.add(data.getColumnHeader(col));
150+
}
151+
152+
// Write headers to CSV
153+
csvFilePrinter.printRecord(headers);
154+
155+
// Write table row-by-row to CSV
156+
for (int row = 0; row < data.getRowCount(); row++) {
157+
List<Object> record = new LinkedList<>();
158+
for (int col = 0; col < data.getColumnCount(); ++col) {
159+
record.add(data.get(col, row));
160+
}
161+
csvFilePrinter.printRecord(record);
162+
}
163+
164+
fileWriter.flush();
165+
}
166+
catch (Exception e) {
167+
log.error(e);
168+
}
169+
}
170+
171+
@Override
172+
public boolean supportsSave(final String source) {
173+
return supportsOpen(source);
174+
}
175+
}

0 commit comments

Comments
 (0)