001package org.intellimate.izou.sdk.frameworks.music.player;
002
003import org.intellimate.izou.resource.ResourceModel;
004
005import java.util.HashMap;
006import java.util.Optional;
007
008/**
009 * The Progress of the current track.
010 * @author LeanderK
011 * @version 1.0
012 */
013@SuppressWarnings("unused")
014public class Progress {
015    /**
016     * if the audio has no specified beginning or end (for example a LiveStream of the audio output of the computer).
017     * THIS DOES NOT MEAN THE INFORMATION IS UNAVAILABLE.
018     */
019    public static long NO_PROGRESS = -1;
020
021    /*
022     * the length of the track in milliseconds.
023     */
024    public static final String lengthDescriptor = "izou.music.progress.length";
025    private final long length;
026    public static final String knownPositionDescriptor = "izou.music.progress.knownPosition";
027    private final long knownPosition;
028    public static final String knownMillisTimeStampDescriptor = "izou.music.progress.knownMillisTimeStamp";
029    private final long knownMillisTimeStamp;
030
031    public Progress(long length, long knownPosition) {
032        this.length = length;
033        this.knownPosition = knownPosition;
034        knownMillisTimeStamp = System.currentTimeMillis();
035    }
036
037    public Progress(long length, long knownPosition, long knownMillisTimeStamp) {
038        this.length = length;
039        this.knownPosition = knownPosition;
040        this.knownMillisTimeStamp = knownMillisTimeStamp;
041    }
042
043    /**
044     * returns the length of the Track in milliseconds
045     * @return the length
046     */
047    public long getLength() {
048        return length;
049    }
050
051    /**
052     * returns the current position in milliseconds
053     * @return the position
054     */
055    public long getPosition() {
056        return knownPosition + (System.currentTimeMillis() - knownMillisTimeStamp);
057    }
058
059    /**
060     * exports the progress
061     * @return a new HashMap
062     */
063    public HashMap<String, Long> export() {
064        HashMap<String, Long> data = new HashMap<>();
065        data.put(lengthDescriptor, length);
066        data.put(knownPositionDescriptor, knownPosition);
067        data.put(knownMillisTimeStampDescriptor, knownMillisTimeStamp);
068        return data;
069    }
070
071    /**
072     * creates a Progress-object from the resourceModel
073     * @param resourceModel the ResourceModel
074     * @return the optional Progress
075     */
076    public static Optional<Progress> importResource(ResourceModel resourceModel) {
077        Object resource = resourceModel.getResource();
078        try {
079            //noinspection unchecked
080            HashMap<String, Long> data = (HashMap<String, Long>) resource;
081            long length = data.get(lengthDescriptor);
082            long knownPosition = data.get(knownPositionDescriptor);
083            long knownTimestamp = data.get(knownMillisTimeStampDescriptor);
084            return Optional.of(new Progress(length, knownPosition, knownTimestamp));
085        } catch (Exception e) {
086            return Optional.empty();
087        }
088    }
089
090    @Override
091    public String toString() {
092        return "Progress{" +
093                "length=" + (length / 60000) + ":" + (length % 60000) +
094                ", knownPosition=" + (knownPosition / 60000) + ":" + (knownPosition % 60000) +
095                ", knownMillisTimeStamp=" + knownMillisTimeStamp +
096                '}';
097    }
098}