//~--- non-JDK imports --------------------------------------------------------

import Dating.Time;

import Exceptions.*;

import LAF.LAF;

import org.jaudiotagger.audio.*;
import org.jaudiotagger.audio.exceptions.*;
import org.jaudiotagger.tag.*;

//~--- JDK imports ------------------------------------------------------------

import java.awt.*;
import java.awt.event.*;
import java.awt.image.*;

import java.io.*;

import java.net.*;

import javax.imageio.*;

import javax.swing.*;
import javax.swing.event.*;

public class audiobookMakerPro extends JFrame implements ListSelectionListener, ActionListener {
    private static Dimension ScreenSize = Toolkit.getDefaultToolkit().getScreenSize();
    static audiobookMakerPro maker;
    private boolean          hasImage = false;
    private Time             time     = new Time(0, 0, 0);

    // private JButton          remove;
    // private JButton          up;
    private BufferedImage Cover;
    private String        CoverName;
    private JPanel        buttonPanel;
    private ButtonGroup   chapterGroup;
    private JButton       chooseImage;
    private JButton       create;
    private File[]        files;

    // private JButton          down;
    // private JList            list;
    // private DefaultListModel mod;
    private int numberOfFiles;

    // private JButton          openFiles;
    private JButton      output;
    private String       outputFolder;
    private JLabel       selectedFolder;
    private JLabel       selectedImage;
    private JRadioButton typeSelf;
    private JRadioButton useFilenames;
    private JRadioButton useNumbers;

    public audiobookMakerPro() {
        this("iPod Audiobook Maker");
    }

    public audiobookMakerPro(String s) {
        super(s);
    }

    public void initComponents() {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        this.setIconImage(new ImageIcon(this.getClass().getResource("/Data\\icon.gif")).getImage());
        setLayout(new FlowLayout());

        // mod  = new DefaultListModel();
        // list = new JList(mod);
        // list.addListSelectionListener(this);
        // list.setVisibleRowCount(20);
        JPanel labelPanel = new JPanel(new FlowLayout());

        selectedFolder = new JLabel("Ordner: <Keiner> -");
        selectedImage  = new JLabel("Cover: <Keins>");
        labelPanel.add(selectedFolder);
        labelPanel.add(selectedImage);
        buttonPanel = new JPanel(new GridLayout(0, 1));

        // openFiles    = new JButton("Öffnen");
        // up           = new JButton("Hoch");
        // down         = new JButton("Runter");
        // remove       = new JButton("Entfernen");
        chooseImage  = new JButton("Cover auswählen");
        output       = new JButton("Ordner");
        create       = new JButton(".POD Datei erstellen");
        chapterGroup = new ButtonGroup();
        useNumbers   = new JRadioButton("Kapitel durchnummerieren", true);
        useFilenames = new JRadioButton("Dateinamen als Kapitelnamen verwenden", false);
        typeSelf     = new JRadioButton("Kapitel selber benennen", false);
        output.setToolTipText(
            "<html><head></head><body><b>Der Name des Unterordners im Slideshow Assembler-Verzeichnis</b>, in dem die Audiodateien liegen<br />und in dem die .POD Datei und die .m4b Datei gespeichert werden sollen</body></html>");
        chooseImage.setToolTipText("Der Name der Bilddatei im \"Ordner\", die als Cover verwendet werden soll");
        useNumbers.setToolTipText("Die Namen der Kapitel werden \"001, 002, ...\" genannt");
        useFilenames.setToolTipText(
            "<html><head></head><body>Die Namen der Kapitel werden nach den Namen der dazugehörigen Dateien benannt.<br>"
            + "Oft werden die Namen dadurch <b>besonders lang</b>.</body></html>");
        typeSelf.setToolTipText("Kapitelnamen selber angeben");

        // openFiles.addActionListener(this);
        // remove.addActionListener(this);
        chooseImage.addActionListener(this);
        output.addActionListener(this);
        create.addActionListener(this);
        chapterGroup.add(useNumbers);
        chapterGroup.add(useFilenames);
        chapterGroup.add(typeSelf);

        // buttonPanel.add(openFiles);
        // buttonPanel.add(up);
        // buttonPanel.add(down);
        // buttonPanel.add(remove);
        buttonPanel.add(labelPanel);
        buttonPanel.add(output);
        buttonPanel.add(chooseImage);
        buttonPanel.add(create);
        buttonPanel.add(useNumbers);
        buttonPanel.add(useFilenames);
        buttonPanel.add(typeSelf);

        try {
            String file = this.getClass().getResource("/Readme.html").getPath();

            file = file.replaceAll("%20", " ");
            file = file.replaceFirst("/", " ");
            System.out.println(file);

            if (new File(file).exists()) {
                try{
                    buttonPanel.add(new frame.JLink(new File(file), "Readme und Tutorial öffnen", Color.BLUE));
                }
                catch(IOException exc){
                    JOptionPane.showMessageDialog(null, "IO");
                    throw new FileNotFoundException();
                }
            }

            /*
             * if(new File(this.getClass().getResource("/Test/Bild.jpg").getFile()).exists()){
             * /                buttonPanel.add(new frame.JLink(new File(this.getClass().getResource("/Test/Bild.jpg").getFile()), "Readme öffnen", Color.BLUE));
             *   buttonPanel.add(new frame.JLink(new File("C:/Documents and Settings/Kim/Desktop/Java/Audiobook Maker/build/classes/Test/Bild.jpg"), "Readme öffnen", Color.BLUE));
             * }
             */
            else {
                throw new FileNotFoundException();
            }
        } catch (FileNotFoundException exc) {
            JOptionPane.showMessageDialog(null, "Readme wech");
        }

        // add(new JScrollPane(list));
        add(buttonPanel);
        pack();
        setLocation((ScreenSize.width - getWidth()) / 2, (ScreenSize.height - getHeight()) / 2);
        setResizable(true);
        setVisible(true);
    }

    public static String castFileToListEntry(File f) {
        String s = "<html><head></head><body><b>" + f.getName() + "</b><br />|->" + f.getAbsolutePath()
                   + "</body></html>";

        return s;
    }

    /*
     * public void addFilesToList(File[] files) {
     *   for (int i = 0; i < files.length; i++) {
     *       addFileToList(files[i]);
     *   }
     * }
     *
     * public void addFileToList(File f) {
     *   this.mod.add(this.numberOfFiles, castFileToListEntry(f));
     *   files[numberOfFiles] = f;
     *   numberOfFiles++;
     *   this.list.repaint();
     * }
     */
    public static void main(String[] args) {
        LAF.setLAF(LAF.Mac);
        maker = new audiobookMakerPro();
        maker.initComponents();
    }

    public void valueChanged(ListSelectionEvent evt) {}

    public void actionPerformed(ActionEvent e) {


        if (e.getActionCommand().equals("Ordner")) {
            outputFolder = JOptionPane.showInputDialog(null, "Bitte Namen des Ordners angeben", "Eingabe",
                    JOptionPane.PLAIN_MESSAGE);

            try {
                File f = new File(outputFolder);

                if (!f.exists() ||!f.isDirectory()) {
                    throw new FolderException();
                }

                files = f.listFiles(new FileFilter() {
                    public boolean accept(File pathname) {
                        return pathname.getName().endsWith(".m4a");
                    }
                });
                selectedFolder.setText("Ordner: " + outputFolder + " -");
                selectedFolder.repaint();
            } catch (FolderException exc) {
                JOptionPane.showMessageDialog(null, "Ordner wurde nicht gefunden", "Fehler", JOptionPane.ERROR_MESSAGE);
                outputFolder = null;
            }
        }

        if (e.getActionCommand().equals("Cover auswählen")) {
            if (outputFolder != null) {
                String s = JOptionPane.showInputDialog(null, "Bitte Namen der Bilddatei eingeben", "Eingabe",
                               JOptionPane.PLAIN_MESSAGE);

                try {
                    if (s == null) {
                        throw new IOException("go");
                    }

                    if (!s.toLowerCase().endsWith(".jpg")) {
                        if (!s.toLowerCase().endsWith(".png")) {
                            throw new EndingException();
                        }
                    }

                    Cover         = ImageIO.read(new File(outputFolder + "\\" + s));
                    this.hasImage = true;
                    selectedImage.setText("Cover: " + s);
                } catch (IOException exc) {
                    if (!exc.getMessage().equals("go")) {
                        Cover = null;
                        JOptionPane.showMessageDialog(null, "Bilddatei wurde nicht gefunden", "Fehler",
                                                      JOptionPane.WARNING_MESSAGE);
                        this.hasImage = false;
                    }
                } catch (EndingException exc) {
                    JOptionPane.showMessageDialog(null, "Das Cover muss eine .jpg oder .png Datei sein", "Fehler",
                                                  JOptionPane.ERROR_MESSAGE);
                    Cover         = null;
                    this.hasImage = false;
                }

                if (Cover != null) {
                    this.hasImage  = true;
                    this.CoverName = s;
                }
            } else {
                JOptionPane.showMessageDialog(null, "Bitte geben sie zuerst einen Ausgabeordner an", "Fehler",
                                              JOptionPane.ERROR_MESSAGE);
            }
        }

        if (e.getActionCommand().equals(".POD Datei erstellen")) {
            this.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));

            try {
                if (outputFolder == null) {
                    throw new NoFolderSelectedException();
                }

                if (files == null) {
                    throw new NoFilesSelectedException();
                }

                if (!hasImage) {
                    if (JOptionPane.showConfirmDialog(null,
                                                      "Es wurde kein Cover ausgewählt.\nDatei trotzdem erstellen?",
                                                      "Kein Cover", JOptionPane.YES_OPTION) == JOptionPane.NO_OPTION) {
                        throw new EndingException();
                    }
                }

                int i = 0;

                try {
                    FileWriter     fWriter = new FileWriter(outputFolder + "\\Podcast.POD");
                    BufferedWriter writer  = new BufferedWriter(fWriter);

                    writer.write("[Podcast]\n");
                    writer.write("altfolder1=" + outputFolder + "\n");
                    writer.write("basename=" + outputFolder + "\n");
                    writer.write("audiobook=true" + "\n");

                    if (this.hasImage) {
                        writer.write("artwork=" + CoverName + "\n");
                        writer.write("imgwidth=" + Cover.getWidth() + "\n");
                        writer.write("imgheight=" + Cover.getHeight() + "\n");
                    }

                    writer.write("editpointcount=" + files.length + "\n\n\n");

                    for (i = 0; i < files.length; i++) {
                        writer.write("[Editpoint_" + (i + 1) + "]\n");

                        if (this.hasImage) {
                            writer.write("image=" + CoverName + "\n");
                        }

                        writer.write("audiofile=" + files[i].getName() + "\n");

                        if (useNumbers.isSelected()) {
                            writer.write("chapter=");

                            if ((i + 1) < 100) {
                                writer.write("0");

                                if ((i + 1) < 10) {
                                    writer.write("0");
                                }
                            }

                            writer.write((i + 1) + "\n");
                        } else if (useFilenames.isSelected()) {
                            writer.write("chapter=" + files[i].getName() + "\n");
                        } else if (typeSelf.isSelected()) {
                            String s = JOptionPane.showInputDialog(null,
                                           "Kapitelname der Datei " + files[i].getName() + " angeben (" + (i + 1)
                                           + " von " + files.length + ")", "Kapitelnamen eingeben",
                                               JOptionPane.PLAIN_MESSAGE);

                            if (s == null) {
                                throw new EndingException();
                            }

                            writer.write("chapter=" + s + "\n");
                        }

                        writer.write("start=" + time.asString() + ".00\n\n");

                        AudioFile af = AudioFileIO.read(files[i]);

                        time.add(0, 0, af.getAudioHeader().getTrackLength());
                    }

                    writer.close();
                    JOptionPane.showMessageDialog(null, "Fertig!\nDas Program schließt automatisch", "Fertig",
                                                  JOptionPane.INFORMATION_MESSAGE);
                    System.exit(0);
                } catch (CannotReadException exc) {
                    JOptionPane.showMessageDialog(null,
                                                  "<html><head></head><body>Die Datei<br><b>" + files[i]
                                                  + "</b><br>konnte nicht gelesen werden</body></html>", "Fehler",
                                                      JOptionPane.ERROR_MESSAGE);
                } catch (TagException exc) {
                    JOptionPane.showMessageDialog(
                        null,
                        "<html><head></head><body>Es ist ein unbekannter Fehler bei der Datei<br><b>" + files[i]
                        + "</b><br>aufgetreten</body></html>", "Fehler", JOptionPane.ERROR_MESSAGE);
                } catch (ReadOnlyFileException exc) {
                    JOptionPane.showMessageDialog(null,
                                                  "<html><head></head><body>Die Datei<br><b>" + files[i]
                                                  + "</b><br>ist eine Read-Only Datei</body></html>", "Fehler",
                                                      JOptionPane.ERROR_MESSAGE);
                } catch (InvalidAudioFrameException exc) {
                    JOptionPane.showMessageDialog(
                        null,
                        "<html><head></head><body>Es ist ein unbekannter Fehler bei der Datei<br><b>" + files[i]
                        + "</b><br>aufgetreten</body></html>", "Fehler", JOptionPane.ERROR_MESSAGE);
                } catch (IOException exc) {
                    JOptionPane.showMessageDialog(null, "Es ist ein unbekannter Fehler aufgetreten", "Fehler",
                                                  JOptionPane.ERROR_MESSAGE);
                }
            } catch (NoFolderSelectedException exc) {
                JOptionPane.showMessageDialog(null, "Bitte wählen sie einen Ausgabeordner an", "Fehler",
                                              JOptionPane.ERROR_MESSAGE);
            } catch (NoFilesSelectedException exc) {
                JOptionPane.showMessageDialog(null, "Es wurden keine Dateien ausgewählt", "Fehler",
                                              JOptionPane.ERROR_MESSAGE);
            } catch (EndingException exc) {}

            this.setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
        }
    }
}


//~ Formatted by Jindent --- http://www.jindent.com
