Package jsynoptic.plugins.jfreechart

Source Code of jsynoptic.plugins.jfreechart.SourceXYDataset$SourceCouple

/* ========================
* JSynoptic : a free Synoptic editor
* ========================
*
* Project Info:  http://jsynoptic.sourceforge.net/index.html
*
* This program is free software; you can redistribute it and/or modify it under the terms
* of the GNU Lesser General Public License as published by the Free Software Foundation;
* either version 2.1 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License along with this
* program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330,
* Boston, MA 02111-1307, USA.
*
* (C) Copyright 2001-2003, by :
*     Corporate:
*         Astrium SAS
*         EADS CRC
*     Individual:
*         Nicolas Brodu
*
* $Id: SourceXYDataset.java,v 1.10 2006/02/15 18:29:06 cazenave Exp $
*
* Changes
* -------
* 25-Sep-2003 : Initial public release (NB);
*
*/

package jsynoptic.plugins.jfreechart;


import java.util.Iterator;
import java.util.Vector;

import jsynoptic.plugins.jfreechart.SourcePieDataset.SourceHolder;

import org.jfree.data.AbstractDataset;
import org.jfree.data.XYDataset;

import simtools.data.DataException;
import simtools.data.DataInfo;
import simtools.data.DataSource;
import simtools.data.DataSourceCollection;
import simtools.data.DataSourceListener;
import simtools.data.DataSourcePool;
import simtools.data.EndNotificationListener;
import simtools.data.UnsupportedOperation;

/**
* @author nbrodu
*
* To change the template for this generated type comment go to
* Window - Preferences - Java - Code Generation - Code and Comments
*/
public class SourceXYDataset extends AbstractDataset implements XYDataset, DataSourceListener, EndNotificationListener {

  static final long serialVersionUID = 2534350549886932663L;
 
  public class SourceCouple  {
    public DataSource x;
    public DataSource y;
    public long startIndex;
    /** Name override. Null => use default*/
    public String name;
    public SourceCouple(DataSource x, DataSource y) {
      this(x,y,0);
    }
    public SourceCouple(DataSource x, DataSource y, long idx) {
        this(x,y,idx,null);
    }
    public SourceCouple(DataSource x, DataSource y, long idx,String name) {
        this.x=x; this.y=y; startIndex = idx; this.name = name;
    }
  }
 
  protected transient Vector sources = new Vector(); // of couples
  protected transient boolean dirty = false; // for source notifications
  protected boolean notifySourceChange = false;
  protected boolean nameAccordingToYOnly = true;
  protected DataInfo info = null;
 
  /**
   * @return
   */
  public boolean isNameAccordingToYOnly() {
    return nameAccordingToYOnly;
  }

  /**
   * @param nameAccordingToYOnly
   */
  public void setNameAccordingToYOnly(boolean nameAccordingToYOnly) {
    this.nameAccordingToYOnly = nameAccordingToYOnly;
  }

  public SourceXYDataset() {
    notifySourceChange = true;
  }

  public SourceXYDataset(DataSourceCollection dsc) {
    setDataSourceCollection(dsc);
    notifySourceChange = true;
  }

  public void setDataSourceCollection(DataSourceCollection dsc) {
    boolean notify = notifySourceChange;
    notifySourceChange = false;
    clear();
    info = dsc.getInformation();
    addXSource((DataSource)dsc.get(0));
    for (int i=1; i<dsc.size(); ++i) {
      addYSource((DataSource)dsc.get(i));
    }
    notifySourceChange = notify;
    if (notifySourceChange) fireDatasetChanged();
  }

  public void setDataSourceCollectionAsCouples(DataSourceCollection dsc) {
    boolean notify = notifySourceChange;
    notifySourceChange = false;
    clear();
    info = dsc.getInformation();
    int i=0;
    for (; i<(dsc.size()&~1);++i) {
      if (i%2==0) addXSource((DataSource)dsc.get(i));
      else addYSource((DataSource)dsc.get(i));
    }
    notifySourceChange = notify;
    if (notifySourceChange) fireDatasetChanged();
  }


  public void addDataSourceCollection(DataSourceCollection dsc) {
    boolean notify = notifySourceChange;
    notifySourceChange = false;
    for (int i=0; i<dsc.size(); ++i) {
      addYSource((DataSource)dsc.get(i));
    }
    notifySourceChange = notify;
    if (notifySourceChange) fireDatasetChanged();
  }

  /** Sets a common X source
   */
  public void setXSource(DataSource ds) {
    if (sources.size()==0) {
      addXSource(ds);
      return;
    }
    for (int i=0; i<sources.size(); ++i) {
      SourceCouple sc = (SourceCouple)sources.get(i);
      if (sc.x!=null) {
          sc.x.removeListener(this);
          sc.x.removeEndNotificationListener(this);
      }
      sc.x = ds;
      sc.x.addListener(this);
      sc.x.addEndNotificationListener(this);
    }
    if (notifySourceChange) fireDatasetChanged();
 

  /** Sets an X source for the given series. If the series does not exists, a new one is created
   * @return the number of the series. This is the same as the argument, except when a new
   * series is created, where this number is the next available regardless of the argument
   */
  public int setXSource(DataSource ds, int i) {
    if (i>=sources.size()) {
      addXSource(ds);
      return sources.size()-1;
    }
    SourceCouple sc = (SourceCouple)sources.get(i);
    if (sc.x!=null) {
        sc.x.removeListener(this);
        sc.x.removeEndNotificationListener(this);
    }
    sc.x = ds;
    sc.x.addListener(this);
    sc.x.addEndNotificationListener(this);
    if (notifySourceChange) fireDatasetChanged();
    return i;
  }

  /** Sets an Y source for the given series. If the series does not exists, a new one is created
   * @return the number of the series. This is the same as the argument, except when a new
   * series is created, where this number is the next available regardless of the argument
   */
  public int setYSource(DataSource ds, int i) {
    if (i>=sources.size()) {
      addYSource(ds);
      return sources.size()-1;
    }
    SourceCouple sc = (SourceCouple)sources.get(i);
    if (sc.y!=null) {
        sc.y.removeListener(this);
        sc.y.removeEndNotificationListener(this);
    }
    sc.y = ds;
    sc.y.addListener(this);
    sc.y.addEndNotificationListener(this);
    if (notifySourceChange) fireDatasetChanged();
    return i;
  }

  public DataSource getXSource(int i) {
    return ((SourceCouple)sources.get(i)).x;
  }

  public DataSource getYSource(int i) {
    return ((SourceCouple)sources.get(i)).y;
  }

  public void addXSource(DataSource ds) {
    if (ds==null) return;
    sources.add(new SourceCouple(ds,null));
    ds.addListener(this);
    ds.addEndNotificationListener(this);
    if (notifySourceChange) fireDatasetChanged();
 

  public void removeXSource(DataSource ds) {
    if (ds==null) return;
    ds.removeListener(this);
    ds.removeEndNotificationListener(this);
    for (Iterator it = sources.iterator(); it.hasNext();) {
      SourceCouple sc = (SourceCouple)it.next();
      if (sc.x.equals(ds)) it.remove();
    }
    if (notifySourceChange) fireDatasetChanged();
 

  public void removeXSource(int i) {
    SourceCouple sc = (SourceCouple)sources.get(i);
    if (sc.x!=null) {
        sc.x.removeListener(this);
        sc.x.removeEndNotificationListener(this);
    }
    if (sc.y!=null) {
        sc.y.removeListener(this);
        sc.y.removeEndNotificationListener(this);
    }
    sources.remove(i);
    if (notifySourceChange) fireDatasetChanged();
 

  /** Adds an y source, using the last set x source
   * X sources shall be set before y sources
   */
  public void addYSource(DataSource ds) {
    if (ds==null) return;
    SourceCouple sc = null;
    if (sources.size()>0) sc = (SourceCouple)sources.lastElement();
    if (sc==null) sources.add(new SourceCouple(null,ds));
    else {
      if (sc.y==null) sc.y = ds;
      else sources.add(new SourceCouple(sc.x,ds));
    }
    ds.addListener(this);
    ds.addEndNotificationListener(this);
    if (notifySourceChange) fireDatasetChanged();
 

  public void removeYSource(DataSource ds) {
    if (ds==null) return;
    ds.removeListener(this);
    ds.removeEndNotificationListener(this);
    for (Iterator it = sources.iterator(); it.hasNext();) {
      SourceCouple sc = (SourceCouple)it.next();
      if (sc.y.equals(ds)) it.remove();
    }
    if (notifySourceChange) fireDatasetChanged();
 

  public void removeYSource(int i) {
    SourceCouple sc = (SourceCouple)sources.get(i);
    if (sc.y!=null) {
        sc.y.removeListener(this);
        sc.y.removeEndNotificationListener(this);
    }
    if (i>0) sources.remove(i);
    else sc.y=null;
    if (notifySourceChange) fireDatasetChanged();
 

  public void add(DataSource x, DataSource y) {
    sources.add(new SourceCouple(x,y));
  }

  public void clear() {
    for (Iterator it = sources.iterator(); it.hasNext();) {
      SourceCouple sc = (SourceCouple)it.next();
      if (sc.x!=null) {
          sc.x.removeListener(this);
          sc.x.removeEndNotificationListener(this);
      }
      if (sc.y!=null) {
          sc.y.removeListener(this);
          sc.y.removeEndNotificationListener(this);
      }
      it.remove();
    }
    info = null;
    if (notifySourceChange) fireDatasetChanged();
  }

  /** Changes the name of the source entry at index i, overrides the default.
   * You can revert to the default name by setting the override to null
   * @param series the series for which to set a name override
   * @param name the new name
   */
  public void setName(int series, String name) {
    SourceCouple sc = (SourceCouple)sources.get(series);
    sc.name = name;
  }

  public void setName(String name) {
    if (info==null) info = new DataInfo(name);
    else info.label = name;
  }

  public String getName() {
    if (info==null) return "";
    return info.label;
  }

  public String getXLabel(int i) {
    String s = DataInfo.getLabel(getXSource(i));
    if (s==null) return "";
    else return s;
  }
 
  public String getYLabel(int i) {
    String s = DataInfo.getLabel(getYSource(i));
    if (s==null) return "";
    else return s;
  }
 
  public int getItemCount(int series) {
    DataSource x = getXSource(series);
    DataSource y = getYSource(series);
    // if x or y is null, nominal case when setting sources separately
    if ((x==null) || (y==null)) return 0;
    try {
      long lastix = x.computeLastIndex();
      if (lastix<0) return 0;
      long startix = x.computeStartIndex();
      if (startix<0) return 0;
      long lastiy = y.computeLastIndex();
      if (lastiy<0) return 0;
      long startiy = y.computeStartIndex();
      if (startiy<0) return 0;
      long starti = Math.max(startix,startiy);
      // Store start for optimization purpose in get[XY]Value below
      ((SourceCouple)sources.get(series)).startIndex = starti;
      int ret =  (int)Math.min(lastix - starti,lastiy - starti)+1;
      return Math.max(ret,0);
    } catch (UnsupportedOperation e) {
    }
    return 0;
  }

  /* (non-Javadoc)
   * @see org.jfree.data.XYDataset#getXValue(int, int)
   */
  public Number getXValue(int series, int item) {
    SourceCouple sc = (SourceCouple)sources.get(series);
    if (sc.x==null) return null;
    Object o = null;
    try {
      o = sc.x.getValue(item+sc.startIndex);
    } catch (DataException e) {
      e.printStackTrace();
    }
    if (o==null) return null;
    if (o instanceof Double) {
      double d = ((Number)o).doubleValue();
      if (Double.isNaN(d)) return null;
      if (Double.isInfinite(d)) return null;
      return (Double)o;
    }
    if (o instanceof Float) {
      float f = ((Number)o).floatValue();
      if (Float.isNaN(f)) return null;
      if (Float.isInfinite(f)) return null;
      return (Float)o;
    }
    if (o instanceof Number) return (Number)o;
    return null;
  }

  /* (non-Javadoc)
   * @see org.jfree.data.XYDataset#getYValue(int, int)
   */
  public Number getYValue(int series, int item) {
    SourceCouple sc = (SourceCouple)sources.get(series);
    if (sc.y==null) return null;
    Object o = null;
    try {
      o = sc.y.getValue(item+sc.startIndex);
    } catch (DataException e) {
      e.printStackTrace();
    }
    if (o==null) return null;
    if (o instanceof Double) {
      double d = ((Number)o).doubleValue();
      if (Double.isNaN(d)) return null;
      if (Double.isInfinite(d)) return null;
      return (Double)o;
    }
    if (o instanceof Float) {
      float f = ((Number)o).floatValue();
      if (Float.isNaN(f)) return null;
      if (Float.isInfinite(f)) return null;
      return (Float)o;
    }
    if (o instanceof Number) return (Number)o;
    return null;
  }

  /** Helper function when a pair isn't fully set */
  public Vector getSources() {
    return sources;
  }

  /* (non-Javadoc)
   * @see org.jfree.data.SeriesDataset#getSeriesCount()
   */
  public int getSeriesCount() {
      int count = sources.size();
      if (count<=0) return count;
      if (((SourceCouple)sources.get(count-1)).y==null) return count -1;
    return count;
  }

  /* (non-Javadoc)
   * @see org.jfree.data.SeriesDataset#getSeriesName(int)
   */
  public String getSeriesName(int series) {
    // Check for overrides
    SourceCouple sc = (SourceCouple)sources.get(series);
    if (sc.name!=null) return sc.name; 
    // Use default
    if (nameAccordingToYOnly) return getYLabel(series);
    else return getYLabel(series) + "/" + getXLabel(series);
  }

// Bridge between listeners from different worlds

  /* (non-Javadoc)
   * @see simtools.data.DataSourceListener#DataSourceValueChanged(simtools.data.DataSource, long, long)
   */
  public void DataSourceValueChanged(DataSource ds, long minIndex, long maxIndex) {
      dirty = true;
  }

  /* (non-Javadoc)
   * @see simtools.data.DataSourceListener#DataSourceIndexRangeChanged(simtools.data.DataSource, long, long)
   */
  public void DataSourceIndexRangeChanged(DataSource ds, long startIndex, long lastIndex) {
      dirty = true;
  }

  /* (non-Javadoc)
   * @see simtools.data.DataSourceListener#DataSourceInfoChanged(simtools.data.DataSource, simtools.data.DataInfo)
   */
  public void DataSourceInfoChanged(DataSource ds, DataInfo newInfo) {
      dirty = true;
  }

  /* (non-Javadoc)
   * @see simtools.data.DataSourceListener#DataSourceValueRangeChanged(simtools.data.DataSource)
   */
  public void DataSourceValueRangeChanged(DataSource ds) {
      dirty = true;
  }

  /* (non-Javadoc)
   * @see simtools.data.DataSourceListener#DataSourceOrderChanged(simtools.data.DataSource, int)
   */
  public void DataSourceOrderChanged(DataSource ds, int newOrder) {
    // Don't care
  }
 
  /* (non-Javadoc)
   * @see simtools.data.DataSourceListener#DataSourceReplaced(simtools.data.DataSource, simtools.data.DataSource)
   */
  public void DataSourceReplaced(DataSource oldData, DataSource newData) {
    for (int i=0; i<sources.size(); ++i) {
      SourceCouple sh = (SourceCouple)sources.get(i);
      if(sh.x==oldData){
        sh.x = newData;
        if(newData!=null){
          sh.x.addListener(this);
          sh.x.addEndNotificationListener(this);
          try {
            sh.startIndex = newData.getLastIndex();
          } catch (UnsupportedOperation e) {
            try {
              sh.startIndex = newData.computeLastIndex();
            } catch (UnsupportedOperation e1) {
              sh.startIndex = 0;
            }
          }
        }
        oldData.removeListener(this);
        oldData.removeEndNotificationListener(this);
        dirty=true;
      }
      if(sh.y==oldData){
        sh.y = newData;
        if(newData!=null){
          sh.y.addListener(this);
          sh.y.addEndNotificationListener(this);
        }
        oldData.removeListener(this);
        oldData.removeEndNotificationListener(this);
        dirty=true;
      }
    }
  }


    /* (non-Javadoc)
     * @see simtools.data.EndNotificationListener#notificationEnd(java.lang.Object)
     */
    public void notificationEnd(Object referer) {
    if (dirty) {
        fireDatasetChanged();
        dirty = false;
    }
    }
 
//  Take care of serialisation. Special handling for datasources

  private void writeObject(java.io.ObjectOutputStream out) throws java.io.IOException {
    out.defaultWriteObject();
    int n = sources.size();
    out.writeInt(n);
    for (int i=0; i<n; ++i) {
      SourceCouple sc = (SourceCouple)sources.get(i);
      DataSourcePool.global.writeDataSource(out, sc.x);
      DataSourcePool.global.writeDataSource(out, sc.y);
      out.writeLong(sc.startIndex);
      out.writeObject(sc.name);
    }
  }

  private void readObject(java.io.ObjectInputStream in) throws java.lang.ClassNotFoundException, java.io.IOException {
    in.defaultReadObject();
    int n =in.readInt();
    sources = new Vector();
    for (int i=0; i<n; ++i) {
      SourceCouple sc;
      sources.add(sc = new SourceCouple(
        DataSourcePool.global.readDataSource(in),
        DataSourcePool.global.readDataSource(in),
        in.readLong()
      ));
      sc.name = (String)in.readObject();
      if (sc.x!=null) {
          sc.x.addListener(this);
          sc.x.addEndNotificationListener(this);
      }
      if (sc.y!=null) {
          sc.y.addListener(this);
          sc.y.addEndNotificationListener(this);
      }
    }
  }

    /* (non-Javadoc)
     * @see java.lang.Object#clone()
     */
    public Object clone() throws CloneNotSupportedException {
        SourceXYDataset c = (SourceXYDataset)super.clone();
        c.sources = new Vector();
        c.info = DataInfo.clone(info);
        // Deep copy, and correct handling of listeners
        for (Iterator it = sources.iterator(); it.hasNext();) {
            SourceCouple sc = (SourceCouple)it.next();
            c.sources.add(c.new SourceCouple(sc.x, sc.y, sc.startIndex, sc.name));
      if (sc.x!=null) {
          sc.x.addListener(c);
          sc.x.addEndNotificationListener(c);
      }
      if (sc.y!=null) {
          sc.y.addListener(c);
          sc.y.addEndNotificationListener(c);
      }
        }
        return c;
    }

    /**
     * @return
     */
    public SourceXYDataset cloneSet() {
        try {
            return (SourceXYDataset)clone();
        } catch (CloneNotSupportedException e) {
            return null;
        }
    }

}

TOP

Related Classes of jsynoptic.plugins.jfreechart.SourceXYDataset$SourceCouple

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.