<!DOCTYPE html>
<html>
<head>
    <!-- [[! Document Settings ]] -->
    <meta charset="utf-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />

    <!-- [[! Page Meta ]] -->
    <title>使用VideoView实现视频开屏页</title>
    <meta name="description" content="与机器，人，神共舞 - 编程，读书，思考，旅行，与机器对话，与人交谈，对神发问，探索，体验人生美丽的风景" />

    <meta name="HandheldFriendly" content="True" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />

    <link rel="shortcut icon" href="/assets/images/favicon.ico" >

    <!-- [[! Styles'n'Scripts ]] -->
    <link rel="stylesheet" type="text/css" href="/assets/css/screen.css" />
    <link rel="stylesheet" type="text/css"
          href="//fonts.googleapis.com/css?family=Merriweather:300,700,700italic,300italic|Open+Sans:700,400" />
    <link rel="stylesheet" type="text/css" href="/assets/css/syntax.css" />
    
    <!-- [[! Ghost outputs important style and meta data with this tag ]] -->
        <link rel="canonical" href="/" />
    <meta name="referrer" content="origin" />
    <link rel="next" href="/page2/" />

    <meta property="og:site_name" content="与机器，人，神共舞" />
    <meta property="og:type" content="website" />
    <meta property="og:title" content="与机器，人，神共舞" />
    <meta property="og:description" content="编程，读书，思考，旅行，与机器对话，与人交谈，对神发问，探索，体验人生美丽的风景" />
    <meta property="og:url" content="/" />
    <meta property="og:image" content="/assets/images/cover1.jpg" />

    <meta name="twitter:card" content="summary_large_image" />
    <meta name="twitter:title" content="与机器，人，神共舞" />
    <meta name="twitter:description" content="编程，读书，思考，旅行，与机器对话，与人交谈，对神发问，探索，体验人生美丽的风景" />
    <meta name="twitter:url" content="/" />
    <meta name="twitter:image:src" content="/assets/images/cover1.jpg" />

    <script type="application/ld+json">
{
    "@context": "http://schema.org",
    "@type": "Website",
    "publisher": "Tao's Page",
    "url": "/",
    "image": "/assets/images/cover1.jpg",
    "description": "编程，读书，思考，旅行，与机器对话，与人交谈，对神发问，探索，体验人生美丽的风景"
}
    </script>

    <meta name="generator" content="Jekyll 3.0.0" />
    <link rel="alternate" type="application/rss+xml" title="与机器，人，神共舞" href="/rss.xml" />

</head>
<body class="post-template nav-closed">

    <div class="nav">
    <h3 class="nav-title">Menu</h3>
    <a href="#" class="nav-close">
        <span class="hidden">Close</span>
    </a>
    <ul>
        <li class="nav-home " role="presentation"><a href="/">Home</a></li>
        <li class="nav-about " role="presentation"><a href="/about.html">About</a></li>
        <li class="nav-fables " role="presentation"><a href="/tag/machine/">Machine</a></li>
        <li class="nav-speeches " role="presentation"><a href="/tag/human/">Human</a></li>
        <li class="nav-fiction " role="presentation"><a href="/tag/god/">God</a></li>
        <li class="nav-author " role="presentation"><a href="/author/hetao/">Author</a></li>
    </ul>
    <a class="subscribe-button icon-feed" href="/rss.xml">Subscribe</a>
</div>
<span class="nav-cover"></span>


    <div class="site-wrapper">

        <!-- [[! Everything else gets inserted here ]] -->
        <!-- < default -->

<!-- The comment above "< default" means - insert everything in this file into -->
    <!-- the [body] of the default.hbs template, which contains our header/footer. -->

<!-- Everything inside the #post tags pulls data from the post -->
<!-- #post -->

<header class="main-header post-head no-cover">
    <nav class="main-nav  clearfix">
        
        
    </nav>
</header>

<main class="content" role="main">

    <article class="post tag-machine">

        <header class="post-header">
            <h1 class="post-title">使用VideoView实现视频开屏页</h1>
            <section class="post-meta">
            <!-- <a href='/'>Tao He</a> -->
            <time class="post-date" datetime="2018-11-28">28 Nov 2018</time>
                <!-- [[tags prefix=" on "]] -->
                 
                on 
                
                    
                       <a href='/tag/machine'>Machine</a>
                       
                
                
            </section>
        </header>

        <section class="post-content">
            
            <p>今天PM提了一个视频开屏页的需求，需要在用户第一次使用时播放一个开屏视频，乍一看，挺简单一需求，但是也或多或少碰到了一些坑，也发现了Android资源编译的一个问题，本着研发之事无小事的原则，还是要记录下踩坑经验和发现的问题。整个实现过程一共两三个小时，逐步解决了以下问题:</p>

<h4>视频全屏</h4>

<p>看到这个问题的第一反应就是把<code>VideoView</code> 的宽高设置为<code>match_parent</code>, 并且保证父容器也是<code>match_parent</code> 根布局, 但是事实没那么简单，视频播放后并没有完全全屏，在我的开发机上视频底部有一条细细的白边，很明显视频没有完全全屏。后来又想到设置<code>MediaPlayer</code>的视频缩放模式:</p>
<div class="highlight"><pre><code class="language-text" data-lang="text">mPlayer.setVideoScalingMode(MediaPlayer.VIDEO_SCALING_MODE_SCALE_TO_FIT_WITH_CROPPING);
</code></pre></div>
<p>设置了两种模式以后都没有效果，这说明<code>VideoView</code>本身没有全屏，没有铺满整个屏幕，所以需要根据屏幕大小动态设置<code>VideoView</code>的尺寸，所以用自定义View实现。
自定义一个继承自<code>VideoView</code>的类来满足要求，具体实现如下:</p>
<div class="highlight"><pre><code class="language-text" data-lang="text">public class FullScreenVideoView extends VideoView {
    public FullScreenVideoView(Context context) {
        super(context);
    }

    public FullScreenVideoView(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public FullScreenVideoView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        int width = getDefaultSize(0, widthMeasureSpec);
        int height = getDefaultSize(0, heightMeasureSpec);
        setMeasuredDimension(width, height);
    }
}
</code></pre></div>
<p>这样比较顺利的实现了全屏，接下来需要解决第二个问题:</p>

<h4>循环播放</h4>

<p>这个比较容易，几乎就是一行代码，是对播放器的设置:</p>
<div class="highlight"><pre><code class="language-text" data-lang="text">mBinding.vvSplash.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
    @Override
    public void onPrepared(MediaPlayer mp) {
        mPlayer = mp;
        mPlayer.setLooping(true);
        mPlayer.setVideoScalingMode(MediaPlayer.VIDEO_SCALING_MODE_SCALE_TO_FIT_WITH_CROPPING);
        mPlayer.start();

        mPlayer.setVideoScalingMode();
    }
});
</code></pre></div>
<p>第三个问题:</p>

<h4>音量切换</h4>

<p>这个问题也比较简单，主要是对播放器的操作，虽然简单但是需要注意以下几个问题:</p>

<ul>
<li>要保证操作的播放器一直是同一个</li>
<li>调用setVolume以后不需要再调用start</li>
<li>恢复音量时最好的方式是通过系统服务(AudioManager)去获取当前音量，但是这个需求只要设置为1就可以了</li>
</ul>

<p>到此，问题都逐一解决了，最后需要记录下一个Android资源编译的问题，问题如下:</p>

<blockquote>
<p>我的工程目录res/drawable下有一个图片文件名为splash.png，开屏视频的MP4文件在res/raw下，名为splash.mp4，编译工程运行后一直报错：
<code>无法播放此视频</code></p>
</blockquote>

<p>当时还以为我代码哪里写错了，检查发现没有错误，后来怀疑路径是不是错了，但断点调试也没问题，就很纳闷，后来拷贝了其它视频播放，发现是正常的，我才想到可能是资源文件名字冲突了，我给开屏视频文件重命名以后一切OK了，冲突在编译期间竟然没有报错，感觉有点坑，这样看来Android在编译资源时并没有区分res/drawable目录和res/raw目录，这个问题需要重视起来，不然会比较恼人。</p>


        </section>

        <footer class="post-footer">

            <!-- Everything inside the #author tags pulls data from the author -->
            <!-- #author-->

            
            <figure class="author-image">
                <a class="img" href="/author/hetao" style="background-image: url(/assets/images/casper.png)"><span class="hidden">'s Picture</span></a>
            </figure>
            

            <section class="author">
                <h4><a href="/author/hetao">Tao He</a></h4>
                
                
                    <p> A computer engineer, reader and thinker.</p>
                
                <div class="author-meta">
                    <span class="author-location icon-location"> Beijing, China</span> 
                    <span class="author-link icon-link"><a href="http://longlinht.github.io/"> longlinht.github.io/</a></span> 
                </div>
            </section>

            <!-- /author  -->

            <section class="share">
                <h4>Share this post</h4>
                <a class="icon-twitter" href="http://twitter.com/share?text=使用VideoView实现视频开屏页&amp;url=http://longlinht.github.io//play-video-in-raw-folder"
                    onclick="window.open(this.href, 'twitter-share', 'width=550,height=235');return false;">
                    <span class="hidden">Twitter</span>
                </a>
                <a class="icon-facebook" href="https://www.facebook.com/sharer/sharer.php?u=http://longlinht.github.io//play-video-in-raw-folder"
                    onclick="window.open(this.href, 'facebook-share','width=580,height=296');return false;">
                    <span class="hidden">Facebook</span>
                </a>
                <a class="icon-google-plus" href="https://plus.google.com/share?url=http://longlinht.github.io//play-video-in-raw-folder"
                   onclick="window.open(this.href, 'google-plus-share', 'width=490,height=530');return false;">
                    <span class="hidden">Google+</span>
                </a>
            </section>
            
            <!-- Add Disqus Comments -->
            
                <div id="disqus_thread"></div>
<script>
    /**
     *  RECOMMENDED CONFIGURATION VARIABLES: EDIT AND UNCOMMENT THE SECTION BELOW TO INSERT DYNAMIC VALUES FROM YOUR PLATFORM OR CMS.
     *  LEARN WHY DEFINING THESE VARIABLES IS IMPORTANT: https://disqus.com/admin/universalcode/#configuration-variables
     */
    /*
    var disqus_config = function () {
        this.page.url = PAGE_URL;  // Replace PAGE_URL with your page's canonical URL variable
        this.page.identifier = PAGE_IDENTIFIER; // Replace PAGE_IDENTIFIER with your page's unique identifier variable
    };
    */
    (function() {  // DON'T EDIT BELOW THIS LINE
        var d = document, s = d.createElement('script');
        
        s.src = '//hetaoof.disqus.com/embed.js';
        
        s.setAttribute('data-timestamp', +new Date());
        (d.head || d.body).appendChild(s);
    })();
</script>
<noscript>Please enable JavaScript to view the <a href="https://disqus.com/?ref_noscript" rel="nofollow">comments powered by Disqus.</a></noscript>

            
            
        </footer>

    </article>

</main>

<aside class="read-next">

    <!-- [[! next_post ]] -->
    
        <a class="read-next-story no-cover" href="http://longlinht.github.io//record-a-debug-process">
            <section class="post">
                <h2>记一次看似困难的Debug</h2>
            </section>
        </a>
    
    <!-- [[! /next_post ]] -->
    <!-- [[! prev_post ]] -->
    
        <a class="read-next-story prev no-cover" href="http://longlinht.github.io//multidex-application-crash">
            <section class="post">
                <h2>MultidexApplication相关的一个crash</h2>
            </section>
        </a>
    
    <!-- [[! /prev_post ]] -->
</aside>

<!-- /post -->


        <footer class="site-footer clearfix">
          <section class="copyright"><a href="/">与机器，人，神共舞</a> &copy; 2021</section>
        </footer>
    </div>
    <!-- [[! Ghost outputs important scripts and data with this tag ]] -->
    <script type="text/javascript" src="https://code.jquery.com/jquery-1.11.3.min.js"></script>
    <!-- [[! The main JavaScript file for Casper ]] -->
    <script type="text/javascript" src="/assets/js/jquery.fitvids.js"></script>
    <script type="text/javascript" src="/assets/js/index.js"></script>

    <!-- Add Google Analytics  -->
        <!-- Google Analytics Tracking code -->
     <script>
	    (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){
	    (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),
	    m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)
	    })(window,document,'script','//www.google-analytics.com/analytics.js','ga');

	    ga('create', 'UA-78960009-1', 'auto');
	    ga('send', 'pageview');

     </script>
   
</body>
</html>
