2012-01-27 27 views
5

Tôi đã quản lý để tải và phát video vimeo bằng các cách sau. Tuy nhiên, autoplay = 1 như được chỉ ra trong vimeo oembed doc s không tự động phát khi tải. Bất cứ ai tìm thấy một cách để tự động chơi (cũng cần phải nắm bắt sự kiện khi video kết thúc)Tự động phát video vimeo trong chế độ xem web trên Android

mWebView.getSettings().setJavaScriptEnabled(true); 
mWebView.getSettings().setAppCacheEnabled(true); 
mWebView.getSettings().setDomStorageEnabled(true); 

// how plugin is enabled change in API 8 
if (Build.VERSION.SDK_INT < 8) { 
    mWebView.getSettings().setPluginsEnabled(true); 
} else { 
    mWebView.getSettings().setPluginState(PluginState.ON); 
} 
mWebView.loadUrl("http://player.vimeo.com/video/24577973?player_id=player&autoplay=1&title=0&byline=0&portrait=0&api=1&maxheight=480&maxwidth=800"); 
+0

là mã ở trên đang hoạt động mà không tự động phát ?? – Venkat

+0

Có, tôi cũng thiết lập một WebViewClient hiển thị/ẩn thanh tiến trình, không chắc chắn nếu thiết lập một hiệu ứng WebViewClient tùy chỉnh không? – scottyab

+0

nhưng tôi đã thử rất nhiều bằng cách sử dụng mã ur.but nó isnot làm việc. vì vậy tôi sử dụng tuỳ chỉnh webview – Venkat

Trả lời

8

Chúng tôi đã đi qua cùng một vấn đề và có vẻ như rằng Android WebView 's (cũng như những người trên iOS) không được lập trình để cho phép tự động bắt đầu video vì có thể nó sẽ ăn vào gói dữ liệu của ai đó. Bạn phải thực sự nhấn vào nó trừ khi bạn muốn lấy WebView của Google làm điểm bắt đầu và cuộn điểm của riêng bạn. Nó không phải là dễ dàng như nó âm thanh, chúng tôi đã cố gắng!

+0

Nghe có vẻ hợp lý rằng các bản xem trước web không được lập trình để làm điều đó, bạn có tìm thấy mã cụ thể trong lớp webview của Android đã dẫn bạn đến kết luận này không? – scottyab

+0

Nó không có mã để ngăn chặn nó, nó là không có mã để làm cho nó xảy ra. – CaseyB

+0

@CaseyB câu trả lời này là từ năm 2012, nó vẫn chính xác? – khizar

10

Câu trả lời này chỉ dành riêng cho Vimeo. Sau khoảng một chục lần thất bại, đây là những gì tôi đã làm việc. Có lẽ nó sẽ giúp người khác. Một nghìn lời xin lỗi cho các tác giả gốc của các câu trả lời SO khác. Tôi đã 'mượn' một số mẫu bên dưới - chỉ nghĩ rằng sẽ thuận tiện khi có tất cả những thứ này ở một nơi và không yêu cầu chúng cho mã của riêng tôi. Trước tiên, tôi không tìm thấy cách nào để nhúng trình phát Vimeo (tức là bạn không thể nhận trực tiếp ở dòng mp4 - ít nhất là không dễ dàng hoặc đáng tin cậy - tôi khá chắc chắn đó là chủ ý). Thứ hai, Vimeo cung cấp một thư viện javascript để cụ cho người chơi của họ, và sử dụng nó là khá khó tránh khỏi. Cẩn thận, nó yêu cầu thông điệp đi qua, đó là một tính năng trình duyệt mới hơn. Đây là tài liệu trên trang API của họ. Thứ ba, như là tài liệu ở nơi khác trên SO, bạn cần phải rất cẩn thận để chờ đợi cho các bộ phận của ngăn xếp để trở thành sẵn sàng, và để không nhảy súng. Thứ tư, máy nghe nhạc Vimeo bao gồm một hình nền đặc biệt không hữu ích có nghĩa là để truyền tải rằng các plugin bị thiếu hoặc bị hỏng (một khung nhỏ của bộ phim, biểu tượng phổ biến cho điều này). Điều thực sự có nghĩa là javascript của bạn đã ném bom ra một nơi nào đó, và không có gì cả. Nếu bạn thấy một chút phim trên màn hình trống, hãy kiểm tra javascript của bạn.

Bước 1. Thiết lập WebView. Bạn có điều này đúng ở trên. Để tham khảo, đây là những gì tôi đã sử dụng.

mWebView = new WebView((Context) this); 
mWebView.setLayoutParams(new LayoutParams(windowWidth, windowHeight)); 

mWebView.getSettings().setJavaScriptEnabled(true); 
// Watch the sdk level here, < 12 requires 'false 
// Wanted to force HTML5/264/mp4, you may want flash 
// where still available 
mWebView.getSettings().setPluginState(PluginState.OFF); 
mWebView.getSettings().setLoadWithOverviewMode(true); 
mWebView.getSettings().setUseWideViewPort(true); 
mWebView.getSettings().setUserAgentString("Android Mozilla/5.0 AppleWebKit/534.30 (KHTML, like Gecko) Version/4.0 Mobile Safari/534.30"); 

wcc = new MyWebChromeClient(); 
mWebView.setWebChromeClient(wcc); 

wvc = new MyWebViewClient(); 
mWebView.setWebViewClient(wvc); 

Bước 2. Bạn cần có WebChromeClient nếu bạn muốn video hoạt động trên WebView. Đó là tài liệu ở đây: http://developer.android.com/reference/android/webkit/WebView.html (Xem Hỗ trợ video HTML).

Một lần nữa, để tham khảo ở đây là những gì tôi đã sử dụng.

private class MyWebChromeClient extends WebChromeClient { 
    @Override 
    public void onProgressChanged(WebView view, int progress) { 
     if(progress == 100) { 
      // Your page is loaded, but not visible, 
      // add whatever navigation elements you plan to use here. 
      // N.B. these are JAVA, not JS nav elements 
     } 
    } 

    @Override 
    public boolean onConsoleMessage(ConsoleMessage cm) { 

    // I like to watch in the console. And, since it was 
    // a very convenient way to monitor the javascript, I 
    // use it for that too. Purists will object, no doubt 

     if(cm.message().equalsIgnoreCase("EVENT -- Finish")) { 
      Log.i(TAG, "---> Finishing . . ."); 
      // Depart the activity 
      finish(); 
     } else { 
      Log.d(TAG, " **Console ["+cm.sourceId()+"] ("+cm.lineNumber()+") ["+cm.message()+"]"); 
     } 
     return(true); 
    } 

     @Override 
     public View getVideoLoadingProgressView() { 
         // Something entertaining while the bytes arrive 
      Log.i(TAG, " -------------> Loading Progress . . . "); 
      LayoutInflater inflater = (LayoutInflater)getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
      return(inflater.inflate(R.layout.loading_video, null)); 
     } 

     @Override 
     public void onShowCustomView(View v, WebChromeClient.CustomViewCallback callback) { 
         // With great sadness, I report that this never fires. 
         // Neither does the 'hide'. 
     } 

     @Override 
     public void onHideCustomView() { 
     } 

} 

Các WebViewClient trông như thế này:

private class MyWebViewClient extends WebViewClient { 

    @Override 
    public void onPageFinished(WebView view, String url) { 
      super.onPageFinished(view, url); 
      String injection = injectPageMonitor(); 
      if(injection != null) { 
      Log.d(TAG, " ---------------> Page Loaded . . ."); 
       Log.d(TAG, " Injecting . . . ["+injection+"]"); 
       view.loadUrl(injection); 
      } 
    } 

} 

Bước 3. Bạn cần phải xây dựng một chút nhỏ bé của Javascript để bắn các cầu thủ. Tôi đã sử dụng điều này:

public String injectPageMonitor() { 
    return("javascript:" + 
       "jQuery(document).ready(function() { " + 
       "console.log(' === Page Ready ===> Setting up');" + 
       "console.log(' ==== Sending PLAY Command ===');" + 
       "var froogaloop = $f('froog');" + 
       "setTimeout(function() { froogaloop.api('play'); }, 3000);" + 
    "});"); 
} 

Giải thích nhanh. . . Tôi sử dụng jQuery trong JS của tôi, đó là đến dưới đây. Đó là chỉ để thuận tiện, bạn có thể làm JS thẳng nếu bạn muốn làm sáng tải. Lưu ý rằng sau khi mọi thứ khác đã sẵn sàng, tập lệnh chờ thêm 3 giây nữa mới thực sự kích hoạt. Trong những khoảnh khắc yếu đuối của tôi, tôi tưởng tượng rằng những người tốt bụng ở Vimeo có một cuộc gọi "sẵn sàng" bị hỏng. 3 giây dường như làm điều đó.

Bước 4. Bạn cần một số HTML và JavaScript trên trang. Tôi đặt nó trong một tập tin văn bản bên trong các tài nguyên (raw/vimeo_frame.html).Các tập tin trông như thế này:

<!DOCTYPE html> 
<html> 
<head> 

<script src="//ajax.googleapis.com/ajax/libs/jquery/1.8.1/jquery.min.js"></script> 
<script type="text/javascript">jQuery.noConflict();</script> 
<script src="http://a.vimeocdn.com/js/froogaloop2.min.js"></script> 

<script type="text/javascript"> 

    jQuery(document).ready(function() { 
     var showing_player = false; 
     var froogaloop = $f('froog'); 

      console.log(' === Page Ready ===> Setting up'); 
     jQuery('.froog_container_class').hide(); 
     jQuery('.console').css('height', '100%'); 

     froogaloop.addEvent('ready', function() { 

      console.log('==== PLAYER READY ====> Setting Play Callback'); 
       froogaloop.addEvent('play', function(data) { 
       console.log('EVENT -- Play'); 
       /* No idea why, but if the player isn't displayed, it goes 
        straight to 'pause'. Probably a feature. So I give it 4x4px 
        to do it's thing during setup */ 
       jQuery('.froog_container_class').show(); 
       jQuery('.froog_container_class').css('height', '4px'); 
       jQuery('.froog_container_class').css('width', '4px'); 
       jQuery('.froog_container_class').css('overflow', 'hidden'); 
      }); 

      /* I don't want to reveal the video until it is actually 
       playing. So I do that here */ 
      var showingPlayer = false; 
      froogaloop.addEvent('playProgress', function(data) { 
       if(!showingPlayer && data.percent > 0) { 
        showingPlayer = true; 
        jQuery('.froog_container_class').show(); 
        jQuery('.froog_container_class').css('height', '_windowHeight'); 
        jQuery('.froog_container_class').css('width', '_windowWidth'); 
        /* Most tablets I tested aren't quick enough to make this work 
        but one can still hope */ 
        jQuery('#loading').fadeOut('slow'); 
       } 
      }); 

     }); 
}); 
</script> 
</head> 
<body> 
<style> 
    body { 
    background-image: url('http://<SomethingEntertainingToWatch>.png'); 
    background-size: contain; 
    } 
    .mask { 
    float: left; 
    height: _windowHeight; 
    width: _windowWidth; 
    z-index: 100; 
    background: transparent; 
    display: inline; 
    position: absolute; 
    top: 0; 
    left: 0; 
    } 
    .froog_container_class { 
     position: absolute; 
     height: _windowHeight; 
     width: _windowWidth; 
     left: 0; 
     top: 0; 
     display: inline; 
     z-index: 1; 
    } 
    #froog { 
     display: inline; 
     height: _windowHeight; 
     width: _windowWidth; 
     postion: absolute; 
     top: 0; 
     left: 0; 
    } 
</style> 
<div id="loading" class="loading"><h1>Loading</h1><img class="loading_anim" src="http://foo.bar.com/assets/global/loading.gif"/> 
</div> 
<!-- Completely optional, I put a div in front of the player to block controls --> 
<div id="mask" class="mask"> 
</div> 
<div id="froog_container" class="froog_container_class"> 
    <iframe id="froog" src="_targetUrl?api=1&title=0&byline=0&portrait=0&player_id=froog" frameborder="0" webkitAllowFullScreen mozallowfullscreen allowFullScreen> 
    </iframe> 
</div> 
</body> 
</html> 

Và tôi tải tập tin html này như sau:

public String genMainHTML() { 
    String code = null; 
    try { 
     Resources res = getResources(); 
     InputStream in_s = res.openRawResource(R.raw.vimeo_frame); 

     byte[] b = new byte[in_s.available()]; 
     in_s.read(b); 
     code = new String(b); 
    } catch (Exception e) { 
     e.printStackTrace(); 
    } 
    if(code != null) { 
      code = code.replaceAll("_windowHeight", "" + windowHeight + "px"); 
      code = code.replaceAll("_windowWidth", "" + windowWidth + "px"); 
      code = code.replaceAll("_targetUrl", targetUrl); 
      return(code); 
    } else { 
      return(null); 
    } 
} 

Và tiêm nó như vậy:

mDomain = "http://player.vimeo.com"; 
mWebView.requestFocus(View.FOCUS_DOWN); 
targetUrl = extras.getString("URL"); 
String meat = genMainHTML(); 
mWebView.loadDataWithBaseURL(mDomain, meat, "text/html", "utf-8", null); 

setContentView(mWebView); 

Whew! Khi WebView đã sẵn sàng, sau đó html và js đi vào, bao gồm iframe với trình phát Vimeo. Khi tài liệu được tải, sau đó chúng tôi chờ cho người chơi trở nên sẵn sàng. Khi người chơi đã sẵn sàng, chúng tôi sẽ thêm một số người nghe. Và 3 giây sau, chúng tôi bắn phương pháp 'chơi' api.

Những người đánh bóng táo này trong khán giả có thể thắc mắc, về tính đầy đủ, cách dừng video? Hai bit. Trước tiên, khi nó kết thúc, tôi dừng nó bằng cách xem đầu ra giao diện điều khiển cho một tin nhắn tôi hiển thị. Như vậy:

public String injectPageFinisher() { 
    return("javascript:" + 
      "jQuery(document).ready(function() { " + 
       "console.log(' === Page Ready ===> Tearing down');" + 
       "console.log(' ==== Sending PAUSE Command ===');" + 
       "var froogaloop = $f('froog');" + 
      "froogaloop.api('pause');" + 
       "jQuery('#froog_container').html('');" + 
      "});"); 
    } 

Mà có thể được chèn vào như vậy:

@Override 
public void onPause() { 
    super.onPause(); 
    if(isFinishing()){ 
     // Unload the page 
     if(mWebView != null) { 
      Log.i(TAG, " ------> Destroying WebView"); 
      mWebView.destroy(); 
     } 
    } 
    finish(); 
} 

Bit thứ hai là nơi mà các video hoàn tất tự nhỏ của nó. Như vậy, trong vimeo_frame.html trên, ngay sau khi 'chơi' gọi lại, tôi đặt:

froogaloop.addEvent('finish', function(data) { 
    console.log('EVENT -- Finish'); 
}); 

Và trong hoạt động, tôi đặt một chút để xem cho điều này - xem ở trên trong override onConsoleMessage.

BAO GIỜ - khi viết bài này, tôi vẫn chưa sắp xếp một vấn đề dai dẳng. MediaPlayer tồn tại sau khi WebView và tất cả các con cháu của nó đã biến mất. Tôi chắc chắn điều này tạo ra một số vấn đề, nhưng tôi chưa xác định được chúng.

+1

Tôi nhận thấy rằng sẵn sàng cũng không bị sa thải. IS IT BROKEN HOẶC IS JUST ANDROID'S WEBVIEW UUUUUUHHHHHGGGGHHHH. –

+0

Tôi khá chắc chắn rằng nó bị hỏng - mặc dù WebView chắc chắn có những thách thức của nó. Vimeo chỉ lặng lẽ làm lại máy nghe nhạc của họ (có thể là 4 tuần trước?).Phải mất một chút để điều chỉnh nó, nhưng giải pháp trên vẫn hoạt động. –

+0

Tôi có Vimeo để làm việc (một lệnh chấp nhận chơi/tạm dừng/tìm kiếm bên ngoài) với mã ít hơn rất nhiều so với điều này, tôi sẽ đăng một câu trả lời ở đây sau khi tôi làm sạch mã một chút. –

0

tôi đã cùng một vấn đề, tôi nghĩ rằng bạn có thể sử dụng cái này để làm cho nó xảy ra:

public abstract trống setMediaPlaybackRequiresUserGesture (boolean yêu cầu)

gia tăng ở mức API 17 Sets liệu WebView yêu cầu cử chỉ người dùng để phát phương tiện. Mặc định là đúng.

Các thông số yêu cầu xem WebView đòi hỏi một cử chỉ dùng để chơi phương tiện truyền thông

Hope để giúp bạn ít nhất một chút!

Các vấn đề liên quan