App zur Steuerung des mpv Mediaplayers auf einem Raspberry Pi über HTTP
ulrich
2021-03-29 cfe3676d7c9667824c52bb5e5c782d4a9a89b672
src/de/uhilger/avdirektor/handler/OMXPlayer.java
@@ -1,11 +1,23 @@
/*
 * To change this license header, choose License Headers in Project Properties.
 * To change this template file, choose Tools | Templates
 * and open the template in the editor.
 */
    AV-Direktor - Control OMXPlayer on Raspberry Pi via HTTP
    Copyright (C) 2021  Ulrich Hilger
    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU Affero General Public License as
    published by the Free Software Foundation, either version 3 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 Affero General Public License for more details.
    You should have received a copy of the GNU Affero General Public License
    along with this program.  If not, see <https://www.gnu.org/licenses/>.
*/
package de.uhilger.avdirektor.handler;
import com.sun.net.httpserver.HttpExchange;
import de.uhilger.avdirektor.App;
import de.uhilger.avdirektor.MeldeThread;
import de.uhilger.avdirektor.ProzessLauscher;
@@ -20,28 +32,65 @@
import java.util.logging.Logger;
/**
 * Methoden zur Ausfuehrung des Programmes omxplayer des Raspberry Pi
 * sowie zum Senden von Kommandos an eine laufende Instanz des
 * omxplayer.
 *
 * Die Klasse OMXPlayer stellt als abstrakte Basisklasse ihre Methoden
 * den Handler-Klassen zur Verfuegung.
 *
 * @author ulrich
 */
public abstract class OMXPlayer implements ProzessLauscher {
public class OMXPlayer implements Player , ProzessLauscher {
  
  private static final Logger logger = Logger.getLogger(OMXPlayer.class.getName());
  
  public static final String BLANK = " ";
  public static final String CMD_DEC_SPEED = "1";
  public static final String CMD_DEC_VOL = "-";
  public static final String CMD_INC_SPEED = "2";
  public static final String CMD_INC_VOL = "+";
  public static final String CMD_NEXT_AUDIO = "k";
  public static final String CMD_NEXT_CHAPTER = "o";
  public static final String CMD_NEXT_SUB = "m";
  public static final String CMD_PAUSE_RESUME = "p";
  public static final String CMD_PREV_AUDIO = "j";
  public static final String CMD_PREV_CHAPTER = "i";
  public static final String CMD_PREV_SUB = "n";
  public static final String CMD_STOP = "q";
  public static final String CMD_TOGGLE_SUB = "s";
  public static final String F_PING = "ping";
  public static final String F_PLAY = "play";
  public static final String F_SEEK = "seek";
  public static final String OPT_HDMI_AUDIO = "-o%20hdmi";
  public static final String OPT_LOCAL_AUDIO = "-o%20local";
  public static final String PFEIL_HERAUF = "5b41";
  public static final String PFEIL_HERUNTER = "5b42";
  public static final String PFEIL_LINKS = "5b44";
  public static final String PFEIL_RECHTS = "5b43";
  public static final String SP_RUECK_30 = "rueck30";
  public static final String SP_RUECK_600 = "rueck600";
  public static final String SP_VOR_30 = "rueck30";
  public static final String SP_VOR_600 = "vor600";
  /**
   * Einen Prozess zum Abspielen mit dem omxplayer starten
   * @param t
   * @param urlStr  URL der Quelle, die abgespielt werden soll
   * @param token
   * @return Antwort des Servers
   */
  public String abspielen(HttpExchange t, String urlStr, String token) {
    return abspielenMitParametern(t, urlStr, null, token);
  /*
  public String abspielen(String urlStr, String token) {
    return abspielenMitParametern(urlStr, null, token);
  }
  */
  
  public String abspielenMitRueckmeldung(HttpExchange t, String urlStr, String meldeUrlStr, String token) {
    return abspielenMitParameternUndRueckmeldung(t, urlStr, null, meldeUrlStr, token);
  /*
  public String abspielenMitRueckmeldung(String urlStr, String meldeUrlStr, String token) {
    return abspielenMitParameternUndRueckmeldung(urlStr, null, meldeUrlStr, token);
  }
  */
  
  /**
   * Einen Prozess zum Abspielen mit dem omxplayer starten 
@@ -50,27 +99,30 @@
  <a href="https://github.com/huceke/omxplayer/blob/master/README.md"target="_blank">Aufstellung der Parameter</a>.Die Zeichenkette parameter enthaelt Eintraege wie z.B.
   * App.OPT_LOCAL_AUDIO oder App.OPT_HDMI_AUDIO.
 Mehrere Parameter werden mit App.BLANK getrennt.
   * @param t
   * @param urlStr  der URL der Quelle, die abgespielt werden soll
   * @param parameter  die Parameter, die vom omxplayer angewendet werden sollen
   * @param token
   * @return Antwort des Servers
   */
  public String abspielenMitParametern(HttpExchange t, String urlStr, String parameter, String token) {
    return abspielenMitParameternUndRueckmeldung(t, urlStr, parameter, null, token);
  /*
  public String abspielenMitParametern(String urlStr, String parameter, String token) {
    return abspielenMitParameternUndRueckmeldung(urlStr, parameter, null, token);
  }
  */
  
  public String abspielenMitParameternUndRueckmeldung(HttpExchange t, String urlStr, String parameter, String meldeUrlStr, String token) {
  @Override
  public String abspielen(String urlStr, String parameter, String meldeUrlStr, String token) {
    String antwort;// = null;
    try {
      Object o = t.getAttribute(App.PI_PLAYER);
      //Object o = t.getAttribute(App.PI_PLAYER);
      Process o = App.getPlayerProcess();
      if(o != null) {
        tilgen(t);
        tilgen();
      }
      StringBuilder kommando = new StringBuilder("omxplayer ");
      if(parameter != null) {
        kommando.append(parameter);
        kommando.append(App.BLANK);
        kommando.append(BLANK);
      }
      if(urlStr.startsWith("http")) {
        kommando.append(urlStr.replace(" ", "%20"));
@@ -104,6 +156,8 @@
        mt.start();
      }
      //servletContext.setAttribute(App.PI_PLAYER, player_process);
      //t.setAttribute(App.PI_PLAYER, player_process);
      App.setPlayerProcess(player_process);
      //Runtime.getRuntime().exec("killall dbus-daemon");
      antwort = "Abspielen gestartet, url: " + urlStr;
    }
@@ -124,19 +178,21 @@
 entfernen und gibt so das Objekt wieder frei fuer die Ausfuehrung 
 weiterer Kommandos.
   *
   * @param t
   * @return die Antwort des Servers
   */
  public String tilgen(HttpExchange t) {
  @Override
  public String tilgen() {
    String antwort; // = null;
    try {
      Object o = t.getAttribute(App.PI_PLAYER);
      //Object o = t.getAttribute(App.PI_PLAYER);
      Process o = App.getPlayerProcess();
      if(o == null) {
        t.setAttribute(App.PI_PLAYER, null);
        //t.setAttribute(App.PI_PLAYER, null);
        App.setPlayerProcess(null);
        // t.removeAttribute(App.PI_PLAYER);
        antwort = "Es ist kein Player zum Beenden vorhanden, aber der Servlet-Kontext wurde bereinigt.";
      } else {
        kommando(t, App.CMD_STOP);
        kommando(CMD_STOP);
        //t.removeAttribute(PI_PLAYER);
        antwort = "Player gestoppt, Kontext bereinigt.";
      }
@@ -150,30 +206,33 @@
  
  /**
   * Dem laufenden Abspielprozess ein Kommando uebermitteln
   * @param t
   * @param k  das Kommando laut 
   * <a href="https://github.com/huceke/omxplayer/blob/master/README.md" target="_blank">Liste der Kommandos</a>
   * @return die Antwort des Servers
   */
  public String kommando(HttpExchange t, String k) {
  @Override
  public String kommando(String k) {
    String antwort; // = null;
    try {
      Object o = t.getAttribute(App.PI_PLAYER);
      //Object o = t.getAttribute(App.PI_PLAYER);
      Process o = App.getPlayerProcess();
      if(o == null) {
        App.setPlayerProcess(null);
        //servletContext.removeAttribute(PI_PLAYER);
        t.setAttribute(App.PI_PLAYER, null);
        //t.setAttribute(App.PI_PLAYER, null);
        antwort = "Es wird nichts abgespielt dem ein Kommando gesendet werden kann.";
      } else {
        Process player_process = (Process) o;
        Process player_process = o;
        OutputStream os = player_process.getOutputStream();
        Writer out = new BufferedWriter(new OutputStreamWriter(os));
        out.write(k);
        out.flush();
        if(k.equals(App.CMD_STOP)) {
        if(k.equals(CMD_STOP)) {
          out.close();
          App.setPlayerProcess(null);
          //player_process.destroy();
          //player_process = null;
          t.setAttribute(App.PI_PLAYER, null);
          //t.setAttribute(App.PI_PLAYER, null);
          //servletContext.removeAttribute(PI_PLAYER);
        }
        antwort = "Kommando '" + k + "' ausgefuehrt.";