2013-04-19 3 views
7

Ich habe vor kurzem begonnen, JFreeChart zu verwenden, und es gibt etwas, das ich tun möchte, aber ich bin nicht sicher, ob es möglich ist. Mein Programm soll ein Spektrogramm (eine Soundgrafik) aus einer WAV-Datei zeichnen. So habe ich es geschafft, die Daten aus meiner WAV-Datei in einer Doppel-Arrayliste zu bekommen und in einem Diagramm darzustellen. Aber jetzt möchte ich in der Lage sein, einen Bereich meines Spektrogramms (mit dem gleichen Werkzeug zum Zoomen) ohne Zoomen zu wählen und nur den ausgewählten Teil meines Sounds abspielen zu können. Aber ich kann einfach keinen Weg zum Erfolg finden. Hier ist mein Code meiner Grafik:JFreeChart wählen Sie einen Bereich ohne zu zoomen

package classes; 

import java.awt.Color; 
import java.awt.Paint; 
import java.awt.Rectangle; 
import java.io.File; 
import java.io.IOException; 

import org.jfree.chart.ChartFactory; 
import org.jfree.chart.ChartUtilities; 
import org.jfree.chart.JFreeChart; 
import org.jfree.chart.plot.Plot; 
import org.jfree.chart.plot.PlotOrientation; 
import org.jfree.chart.plot.XYPlot; 
import org.jfree.data.xy.XYSeries; 
import org.jfree.data.xy.XYSeriesCollection; 
import org.jfree.ui.RectangleInsets; 

public class Chart{ 
    JFreeChart chart; 
    Plot plot; 

    //Constructeur de la classe Chart 
    public Chart(double[][] bs, int channel, int framesLength, float frameRate) 
    { 
     // Création d'un XY chart 
     XYSeries series = new XYSeries("XYGraph"); 
     int i=0,j=0; 
     float k=0; 
     //Ajout de tous les points du tableau de 16 bytes dans le chart 
     for(i=0; i <channel;i++) 
     { 
      for(j=0; j< framesLength;j++) 
      { 
       //Division des valeurs par 2^15 pour être entre 1 et -1 
       series.add(k, (bs[i][j]/32768)); 
       //Echelle de X 
       k+=(1/frameRate); 
      } 
     } 
     // Ajoute la série au dataset 
     XYSeriesCollection dataset = new XYSeriesCollection(); 
     dataset.addSeries(series); 
     // Génération du graphe 
     chart = ChartFactory.createXYLineChart(
     "Ajouter titre à la fonction de génération", // Titre 
     "Temps (s)", // Nom de l'axe X 
     "y-axis", // Nom de l'axe Y 
     dataset, // Dataset 
     PlotOrientation.VERTICAL, // Plot Orientation 
     true, // Show Legend 
     false, // Use tooltips 
     false // Configure chart to generate URLs? 
     ); 
     plot= (XYPlot) chart.getPlot(); 

    } 
    //Renvoie le chart 
    public JFreeChart getChart() 
    { 
     return chart; 
    } 

    public void color(Color c) 
    { 
     plot.setBackgroundPaint(c); 
    } 
} 

Und hier ich das Diagramm Klasse bin aufrufen und verwenden es:

Chart chartUn= new Chart(bs, channels , frameLength , frameRate); 
     chartUn.color(Color.pink); 
     vue.setChartPanelUn(new ChartPanel(chartUn.getChart(), false)); 
     vue.getChartPanelUn().setRangeZoomable(false); 
     vue.getChartPanelUn().setMouseWheelEnabled(true); 

vue.getChartPanelUn() gibt einen ChartPanel. Würdest du eine Idee haben, wie ich mein Problem lösen kann? Vielen Dank (Und sorry, wenn mein Englisch ist nicht immer genau: /)

Antwort

12

Diese Mitteilung nicht durch Zoomen Verwenden Sie dazu ein MouseListener zu Ihrem ChartPanel hinzugefügt, um ein Marker zur Domain Achse hinzuzufügen.

In diesem Beispiel habe ich MouseAdapter subclassed, so dass wenn Sie die Maustaste gedrückt halten wird der Domänenwert erfasst (markerStart) und wenn Sie die Maus Endposition freigegeben wird ('markerEnd') und ein Marker zum Plot hinzugefügt wird (updateMarker)

Sie werden dann eine Tabelle wie folgt erhalten:

Chart with Domain Marker

Beachten Sie, dass in diesem Beispiel habe ich tatsächlich den Zoom ausgeschaltet.

import java.awt.Color; 
import java.awt.event.MouseAdapter; 
import java.awt.event.MouseEvent; 
import java.awt.geom.Point2D; 
import java.awt.geom.Rectangle2D; 

import javax.swing.JFrame; 
import javax.swing.JPanel; 

import org.jfree.chart.ChartFactory; 
import org.jfree.chart.ChartPanel; 
import org.jfree.chart.JFreeChart; 
import org.jfree.chart.plot.IntervalMarker; 
import org.jfree.chart.plot.Marker; 
import org.jfree.chart.plot.PlotOrientation; 
import org.jfree.chart.plot.XYPlot; 
import org.jfree.chart.renderer.xy.XYLineAndShapeRenderer; 
import org.jfree.data.xy.XYDataset; 
import org.jfree.data.xy.XYSeries; 
import org.jfree.data.xy.XYSeriesCollection; 
import org.jfree.ui.Layer; 


public class MouseMarkerDemo extends JFrame { 


    public MouseMarkerDemo(String title) { 
     super(title); 
     JPanel chartPanel = createDemoPanel(); 
     chartPanel.setPreferredSize(new java.awt.Dimension(500, 270)); 
     setContentPane(chartPanel); 
    } 


    private final static class MouseMarker extends MouseAdapter{ 
     private Marker marker; 
     private Double markerStart = Double.NaN; 
     private Double markerEnd = Double.NaN; 
     private final XYPlot plot; 
     private final JFreeChart chart; 
     private final ChartPanel panel; 


     public MouseMarker(ChartPanel panel) { 
      this.panel = panel; 
      this.chart = panel.getChart(); 
      this.plot = (XYPlot) chart.getPlot(); 
     } 

     private void updateMarker(){ 
      if (marker != null){ 
       plot.removeDomainMarker(marker,Layer.BACKGROUND); 
      } 
      if (!(markerStart.isNaN() && markerEnd.isNaN())){ 
       if (markerEnd > markerStart){ 
        marker = new IntervalMarker(markerStart, markerEnd); 
        marker.setPaint(new Color(0xDD, 0xFF, 0xDD, 0x80)); 
        marker.setAlpha(0.5f); 
        plot.addDomainMarker(marker,Layer.BACKGROUND); 
       } 
      } 
     } 

     private Double getPosition(MouseEvent e){ 
      Point2D p = panel.translateScreenToJava2D(e.getPoint()); 
      Rectangle2D plotArea = panel.getScreenDataArea(); 
      XYPlot plot = (XYPlot) chart.getPlot(); 
      return plot.getDomainAxis().java2DToValue(p.getX(), plotArea, plot.getDomainAxisEdge()); 
     } 

     @Override 
     public void mouseReleased(MouseEvent e) { 
      markerEnd = getPosition(e); 
      updateMarker(); 
     } 

     @Override 
     public void mousePressed(MouseEvent e) { 
      markerStart = getPosition(e); 
     } 
    } 

    private static XYDataset createDataset() { 

     XYSeries series1 = new XYSeries("Data"); 
     series1.add(1.0, 1.0); 
     series1.add(2.0, 4.0); 
     series1.add(3.0, 3.0); 
     series1.add(4.0, 5.0); 
     series1.add(5.0, 5.0); 
     series1.add(6.0, 7.0); 
     series1.add(7.0, 7.0); 
     series1.add(8.0, 8.0); 

     XYSeriesCollection dataset = new XYSeriesCollection(); 
     dataset.addSeries(series1); 
     return dataset; 

    } 


    private static JFreeChart createChart(XYDataset dataset) { 

     JFreeChart chart = ChartFactory.createXYLineChart(
      "Mouse Marker", 
      "X", 
      "Y", 
      dataset, 
      PlotOrientation.VERTICAL, 
      true, 
      true, 
      false 
     ); 
     XYPlot plot = (XYPlot) chart.getPlot(); 
     plot.setDomainPannable(true); 
     plot.setRangePannable(true); 
     XYLineAndShapeRenderer renderer 
       = (XYLineAndShapeRenderer) plot.getRenderer(); 
     renderer.setBaseShapesVisible(true); 
     renderer.setBaseShapesFilled(true); 
     return chart; 
    } 

    public static JPanel createDemoPanel() { 
     final JFreeChart chart = createChart(createDataset()); 
     final ChartPanel panel = new ChartPanel(chart); 
     panel.setRangeZoomable(false); 
     panel.setDomainZoomable(false); 
     panel.addMouseListener(new MouseMarker(panel)); 
     return panel; 
    } 

    public static void main(String[] args) { 
     MouseMarkerDemo demo = new MouseMarkerDemo("JFreeChart: MouseMarkerDemo.java"); 
     demo.pack(); 
     demo.setVisible(true); 
    } 

} 
+0

Danke für die schnelle Antwort! Ich werde es dieses Wochenende versuchen, um zu sehen, ob es mit meinem Code funktioniert – user2299206

Verwandte Themen