fiore@3: /*
fiore@3: CCmI Editor - A Collaborative Cross-Modal Diagram Editing Tool
fiore@3:
fiore@3: Copyright (C) 2011 Queen Mary University of London (http://ccmi.eecs.qmul.ac.uk/)
fiore@3:
fiore@3: This program is free software: you can redistribute it and/or modify
fiore@3: it under the terms of the GNU General Public License as published by
fiore@3: the Free Software Foundation, either version 3 of the License, or
fiore@3: (at your option) any later version.
fiore@3:
fiore@3: This program is distributed in the hope that it will be useful,
fiore@3: but WITHOUT ANY WARRANTY; without even the implied warranty of
fiore@3: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
fiore@3: GNU General Public License for more details.
fiore@3:
fiore@3: You should have received a copy of the GNU General Public License
fiore@3: along with this program. If not, see .
fiore@3: */
fiore@3: package uk.ac.qmul.eecs.ccmi.checkboxtree;
fiore@3:
fiore@3: import java.io.BufferedReader;
fiore@3: import java.io.BufferedWriter;
fiore@3: import java.io.File;
fiore@3: import java.io.FileReader;
fiore@3: import java.io.FileWriter;
fiore@3: import java.io.IOException;
fiore@3: import java.util.Collection;
fiore@3: import java.util.Collections;
fiore@3: import java.util.HashSet;
fiore@3: import java.util.Iterator;
fiore@3: import java.util.Set;
fiore@3:
fiore@3: /**
fiore@3: * The {@code SetProperties} class represents a persistent set of properties.
fiore@3: * The {@code SetProperties} can be saved to a stream or loaded from a stream.
fiore@3: *
fiore@3: * Unlike {@code java.util.Properties}, this class is not backed by a key-value map, but rather
fiore@3: * by a {@code Set}. Therefore it only contains values. All the methods of this class are thread-safe,
fiore@3: * but {@code iterator()}. In order to safely iterate on the Set, the iteration must happen in a block syncronized
fiore@3: * on the Object returned by {@link #getMonitor()}.
fiore@3: *
fiore@3: * For a description of the methods of the {@code Set} interface, see {@code java.util.Set}
fiore@3: *
fiore@3: * @see java.util.Properties
fiore@3: * @see java.util.Collections#synchronizedSet(Set)
fiore@3: */
fiore@3: public class SetProperties implements Set {
fiore@3: public SetProperties() {
fiore@3: delegate = Collections.synchronizedSet(new HashSet());
fiore@3: }
fiore@3:
fiore@3: public SetProperties(Collection extends String> collection) {
fiore@3: delegate = Collections.synchronizedSet(new HashSet(collection));
fiore@3: }
fiore@3:
fiore@3: public SetProperties(int initialCapacity) {
fiore@3: delegate = Collections.synchronizedSet(new HashSet(initialCapacity));
fiore@3: }
fiore@3:
fiore@3: public SetProperties(int initialCapacity, float loadFactor){
fiore@3: delegate = Collections.synchronizedSet(new HashSet(initialCapacity, loadFactor));
fiore@3: }
fiore@3:
fiore@3: /* DELEGATE METHODS */
fiore@3: @Override
fiore@3: public boolean add(String arg0) {
fiore@3: return delegate.add(arg0);
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public boolean addAll(Collection extends String> arg0) {
fiore@3: return delegate.addAll(arg0);
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public void clear() {
fiore@3: delegate.clear();
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public boolean contains(Object arg0) {
fiore@3: return delegate.contains(arg0);
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public boolean containsAll(Collection> arg0) {
fiore@3: return delegate.containsAll(arg0);
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public boolean equals(Object arg0) {
fiore@3: return delegate.equals(arg0);
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public int hashCode() {
fiore@3: return delegate.hashCode();
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public boolean isEmpty() {
fiore@3: return delegate.isEmpty();
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public Iterator iterator() {
fiore@3: return delegate.iterator();
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public boolean remove(Object arg0) {
fiore@3: return delegate.remove(arg0);
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public boolean removeAll(Collection> arg0) {
fiore@3: return delegate.removeAll(arg0);
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public boolean retainAll(Collection> arg0) {
fiore@3: return delegate.retainAll(arg0);
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public int size() {
fiore@3: return delegate.size();
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public Object[] toArray() {
fiore@3: return delegate.toArray();
fiore@3: }
fiore@3:
fiore@3: @Override
fiore@3: public T[] toArray(T[] arg0) {
fiore@3: return delegate.toArray(arg0);
fiore@3: }
fiore@3:
fiore@3: /**
fiore@3: * Stores the content of this set (strings) in a text file. The content can then be retrieved
fiore@3: * by calling {@code load()} passing as argument the same file as this method. The strings
fiore@3: * will be written on a row each.
fiore@3: *
fiore@3: * @param file A valid File where the content of this object will be stored
fiore@3: * @param comments A comment string that will be added at the beginning of the file.
fiore@3: *
fiore@3: * @throws IOException if an exception occurs while writing the file
fiore@3: */
fiore@3: public void store(File file, String comments) throws IOException{
fiore@3: synchronized(delegate){
fiore@3: if(file == null)
fiore@3: throw new IllegalArgumentException("File cannot be null");
fiore@3: FileWriter fWriter = new FileWriter(file);
fiore@3: BufferedWriter writer = new BufferedWriter(fWriter);
fiore@3: if(comments != null){
fiore@3: writer.write(COMMENTS_ESCAPE+" "+comments);
fiore@3: writer.newLine();
fiore@3: writer.newLine();
fiore@3: }
fiore@3:
fiore@3: for(String property : this){
fiore@3: writer.write(property);
fiore@3: writer.newLine();
fiore@3: }
fiore@3: writer.close();
fiore@3: }
fiore@3: }
fiore@3:
fiore@3: /**
fiore@3: * Loads the content of a file into this set. Whaen the file is read, each row is taken as an
fiore@3: * entry of the set.
fiore@3: *
fiore@3: * @param file the file where to read the entries from
fiore@3: * @throws IOException if an exception occurs while reading the file
fiore@3: */
fiore@3: public void load(File file) throws IOException{
fiore@3: synchronized(delegate){
fiore@3: if(file == null)
fiore@3: throw new IllegalArgumentException("File cannot be null");
fiore@3: FileReader fReader = new FileReader(file);
fiore@3: BufferedReader reader = new BufferedReader(fReader);
fiore@3: String line;
fiore@3: while((line = reader.readLine()) != null){
fiore@3: if(!line.isEmpty() && !line.trim().startsWith(COMMENTS_ESCAPE))
fiore@3: add(line);
fiore@3: }
fiore@3: reader.close();
fiore@3: }
fiore@3: }
fiore@3:
fiore@3: /**
fiore@3: * Returns the Object all the methods (but {@code iterator()} of this {@code Set} are synchronized on. It can be used
fiore@3: * to safely iterate on this object without incurring in a race condition
fiore@3: *
fiore@3: * @return an {@code Object} to be used as synchronization monitor
fiore@3: *
fiore@3: * @see java.util.Collections#synchronizedSet(Set)
fiore@3: */
fiore@3: public Object getMonitor(){
fiore@3: return delegate;
fiore@3: }
fiore@3:
fiore@3: private Set delegate;
fiore@3: private static String COMMENTS_ESCAPE = "#";
fiore@3: }