#!/usr/bin/perl use Shell; use strict; use POSIX qw(floor); # Written by Bob Igo from the MythTV Store at http://MythiC.TV # including some original code and contributions from Nick C. # and graysky. # Email: bob@stormlogic.com # # If you run into problems with this script, please send me email # PURPOSE: # -------------------------- # This is a wrapper script that tries to find the best parameters # for calling an underlying video player. The outer layer determines # the best playback parameters, while the inner layer picks the best # player to call. # RATIONALE: # -------------------------- # Default video playback options are not optimal on all hardware or # for all video types. In addition, common video players do not # offer to bookmark video so that you can resume where you left off. # Both of these problems can be addressed by this wrapper. # PARAMETERS: # -------------------------- # The same parameters you'd use for mplayer, some of which may be # translated automatically for use with smplayer. # FILES: # -------------------------- # $mediafile, the file to play sub run () { my $mediafile = @ARGV[$#ARGV]; my $player = &pick_player(); # mplayer evaluates configuration options in the following order, with # later-evaluated options overriding earlier-evaluated ones, both within # a given configuration location and between them: # 1) system-wide configuration/profiles, /etc/mplayer/mplayer.conf # 2) user-specific configuration/profiles, ~/.mplayer/config # 3) commandline configuration parameters # 4) file-specific configuration, ~/.mplayer/[filename].conf # 5) any nonstandard configuration file, included via "-include" parameter # # This script's dynamic configuration options fall in at 2.5 above, # so commandline options, file-specific configuration options, # or a nonstandard configuration file will override the options that # the script creates, but system-wide and user-specific configuration # will be overridden by the dynamic configuration options. # # This is sub-optimal, as the easiest way for a user to compensate for # a misfiring configuration rule would be to override it in a configuration # file. Instead, they will have to change the way they run this script. my $player_parameters = join(' ', &dynamic_parameters($mediafile), &translate_parameters($player,@ARGV[0..$#ARGV-1])); &player($player,$player_parameters,$mediafile); } &run(); # Translates any parameters into ones that will be compatible with the given player. sub translate_parameters() { my($player,@parameters)=@_; if ($player eq "smplayer") { # Stupidly, smplayer uses a different set of command-line parameters than generic # mplayer, so we need to translate mplayer-centric ones into the few that are # available in smplayer-ese. my %smplayer_parameter_translation_array = ( "-fs" => "-fullscreen", "-zoom" => " " ); sub translate() { my($flag)=@_; return $smplayer_parameter_translation_array{$flag}; } return map(&translate($_), @parameters); } else { # currently, all other players used by this wrapper work with mplayer parameters return @parameters; } } # Returns an array of dynamic parameters based on the media type, # the presence of special playback decoding hardware, and the # general capability of the CPU. sub dynamic_parameters () { my($mediafile)=@_; my @parameters = (); my $codec=""; # figure out what codec the video uses my $command="mplayer -identify -vo null -frames 0 \"$mediafile\" | grep ID_VIDEO_CODEC | cut -c 16- |"; open(SHELL, $command); while () { chop; $codec = $_; #print "DEBUG: codec is $codec\n"; } close(SHELL); # We should use vdpau if it's available and helps with the codec we need to decode. # ??? NOTE: At the moment, vdpau capability is assumed, not verified. if ($codec eq "ffh264") { # h.264 push(@parameters, "-vo vdpau"); push(@parameters, "-vc ffh264vdpau"); } elsif ($codec eq "ffmpeg2") { # MPEG2 push(@parameters, "-vo vdpau"); push(@parameters, "-vc ffmpeg12vdpau"); # problems have been reported with WMV3 support # } elsif ($codec eq "ffwmv3") { # WMV3 # push(@parameters, "-vo vdpau"); # push(@parameters, "-vc ffwmv3vdpau"); # problems have been reported with WVC1 support # } elsif ($codec eq "ffvc1") { # WVC1 # push(@parameters, "-vo vdpau"); # push(@parameters, "-vc ffvc1vdpau"); } else { push(@parameters, "-vo xv,x11,"); push(@parameters, "-vc ,"); } push(@parameters, "-vf pp=lb,"); return(@parameters); } # Find the best player for use on this system. The script prefers smplayer, # which has built-in bookmarking, falling back to mplayer-resumer.pl, which # implements bookmarking as an mplayer wrapper, if smplayer cannot be found. # Finally, if no bookmarking players can be found, a barebones mplayer is used. sub pick_player () { #my @possible_players = ("smplayer", "mplayer-resumer.pl", "mplayer"); my @possible_players = ("mplayer-resumer.pl", "mplayer"); my $command; my $candidate_player; foreach (@possible_players) { $candidate_player = $_; $command = "which $candidate_player |"; open(SHELL, $command); if () { #print "player $candidate_player : $_\n"; return $candidate_player; } close(SHELL); } } # Calls player sub player () { my($player,$parameters,$mediafile)=@_; my $command = "$player $parameters \"$mediafile\" 2>&1 |"; print "DEBUG: $0's player command is: *** $command ***\n"; open(SHELL, $command); while () { print $_; } close(SHELL); }