web-dev-qa-db-ja.com

ダウンロード時に新しいタブを開いたり閉じたりする

多くのウェブサイト(Dropboxが良い例です)では、ドキュメントをクリックしてダウンロードすると、新しいウィンドウ/タブが開き、ダウンロードしますプロンプトが表示され、タブ/ウィンドウはすぐに閉じます(プロンプトは開いたままです)。

Javascriptを使用してこの動作を複製するにはどうすればよいですか?

1つのアプローチは、そのダウンロードプロンプトの外観を検出してから、window.close()を使用することだと思います。ただし、その特定のプロンプトを検出する方法がわかりません。

クロスブラウザソリューションが推奨されますが、Firefoxで機能するものは何でも大歓迎です。

説明

  1. 私はこれをGreasemonkeyスクリプトで行っています
  2. 新しいタブで開く「リンク」は、必ずしもドキュメントへの直接リンクではありません。場合によっては、バックグラウンドでダウンロードを開始する単純なページです。特別な「ダウンロード」ページがあるサイトの種類を指します...「ダウンロードはまもなく開始されます。開始されない場合は、ここをクリックしてください」などのサイトがあります。

詳細説明:上記の説明2で説明したウェブサイトの種類に関して、私がやりたいのは、ダウンロードリンクをクリックし、その特定のダウンロードページを新しいウィンドウにロードして、ウィンドウを表示することです。ダウンロードが開始されたら閉じます。

11
skittleys

あなたが望むものには3つの基本的な部分があります:

  1. ダウンロードリンクを傍受する必要があります。
  2. _target="_blank"_で変更するだけでなく、クリックしたときに新しいタブにリンクを送信する必要があります。タブはjavascriptで開く必要があります。これにより、時が来たときにjavascriptでタブを閉じることができます。
  3. スクリプトは、ポップアップを閉じるタイミングを検出できるように、「ポップアップ」タブを実行/処理する必要もあります。

この議論については、参照 jsFiddleのこのテストページこれは次のように構成されています。

_<div id="downloadLinks">
  <ul>
    <li><a class="dwnPageLink" href="http://fiddle.jshell.net/cDTKj/show/">
            Test file, download page at jsFiddle
        </a>
    </li>
    <li><a class="dwnPageLink" href="http://dw.com.com/redir...">
            TextPad (a great text editor), download page at CNET / Download
        </a>
    </li>
  </ul>
</div>
_

ここで、_a.dwnPageLink_リンクはそれぞれ「ダウンロードページ」を開きます。これは、少し遅れてファイルのダウンロードを自動的に開始します。


ダウンロードリンクを傍受する(_a.dwnPageLink_):

次のようにリンクをインターセプトします。

_$("#downloadLinks a.dwnPageLink").each (interceptLink);

function interceptLink (index, node) {
    var jNode   = $(node);
    jNode.click (openInNewTab);
    jNode.addClass ("intercepted");
}
_

影響を受けたリンクをすばやく確認できるように、CSSクラスも追加していることに注意してください。
openInNewTabの詳細を以下に示します。タブを開き、通常のリンクアクションを停止する必要があります。


新しいタブへのリンクを送信します。

リンクを処理するには、window.open()を使用する必要があります。ページが_window.open_で開かれていない場合、スクリプトはページを閉じることができません。

GM_openInTab() は、_window.opener_が正しく設定されないため、または開いているタブを閉じるメカニズムが提供されないため、使用できないことに注意してください。

新しいタブはopenInNewTabで起動され、次のようになります。

_function openInNewTab (zEvent) {
    //-- Optionally adjust the href here, if needed.
    var targURL     = this.href;
    var newTab      = window.open (targURL, "_blank");

    //--- Stop the link from doing anything else.
    zEvent.preventDefault ();
    zEvent.stopPropagation ();
    return false;
}
_


「ポップアップ」タブを処理します。

起動ページから[ファイル]ダイアログを監視することはできません。したがって、「ポップアップ」タブでも実行するようにスクリプトを設定する必要があります。それに応じて_@include_ディレクティブを追加します。

スクリプトのポップアップ部分は、beforeunloadイベントを監視することで[ファイル]ダイアログを検出できます。ブラウザは、[ファイル]ダイアログを開く直前(およびタブが閉じる直前)にbeforeunloadイベントを発生させますが、これは無視できます。

ただし、ダイアログが表示されたときにタブを閉じることはできません。これを行うと、ダイアログも閉じます。そのため、少しの時間遅延と[確認]ダイアログを追加して、[ファイル]ダイアログが閉じるまでタブが開いたままになるようにします。確認ダイアログをクリアするには、 Enter 延長戦(またはクリック[〜#〜] ok [〜#〜])。

コードは次のようになります。

_$(window).bind ("beforeunload",  function (zEvent) {
    //-- Allow time for the file dialog to actually open.
    setTimeout ( function () {
            /*-- Since the time it takes for the user to respond
                to the File dialog can vary radically, use a confirm
                to keep the File dialog open long enough for the user 
                to act.
            */
            var doClose = confirm ("Close this window?");
            if (doClose) {
                window.close ();
            }
        },
        444 // 0.444 seconds
    );
} );
_


注意:

  1. スクリプトは「リスト」ページと「ダウンロード」ページの両方で実行されるため、_window.opener_をチェックすることでどちらがどちらであるかを判断できます。 javascriptで開かれたページでは、これはnull以外の値になります。
  2. この質問では、タブをバックグラウンドでロードすることについては尋ねていませんでした。これは、成功の度合いはさまざまですが、より複雑になります。そのために新しい質問をしてください。


完全なスクリプト:

このスクリプトは テストページ および CNET /ダウンロードページ で機能します:

_// ==UserScript==
// @name        _Download page, auto closer
// @namespace   _pc
// ******** Includes for "List pages" that have the links we might click...
// @include     http://YOUR_SERVER.COM/YOUR_LIST-PAGE_PATH/*
// @include     http://jsbin.com/ozofom/*
// @include     http://fiddle.jshell.net/qy3NP/*
// @include     http://download.cnet.com/*
// ******** Includes for "Popup pages" that do the actual downloads...
// @include     http://YOUR_SERVER.COM/YOUR_POPUP-PAGE_PATH/*
// @include     http://fiddle.jshell.net/cDTKj/*
// @include     http://dw.com.com/redir?*
// @require     http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js
// @grant       GM_addStyle
// @grant       GM_openInTab
// ==/UserScript==
/*- Important: The @include or @match directives must for for both the pages
    that list the download links, AND the pages that do the actual downloading.

    The @grant directive is needed to work around a design change
    introduced in GM 1.0.   It restores the sandbox.
*/

var bPageNotOpenedByJavascript = window.opener ? false : true;
if (bPageNotOpenedByJavascript) {
    /***** "Normal" page, which might contain links to special download pages.
    */
    //--- Intercept links to the download pages:
    // For our jsFiddle Test page:
    $("#downloadLinks a.dwnPageLink").each (interceptLink);

    // For CNET/Download:
    $("#downloadLinks div.dlLinkWrapper a").each (interceptLink);

    GM_addStyle ( "                                 \
        a.intercepted {                             \
            background:         Lime;               \
        }                                           \
    " );
}
else {
    /***** Page opened by JS in either a popup or new tab.
        This was *most likely* done by us, using window.open.
    */
    $(window).bind ("beforeunload",  function (zEvent) {
        //-- Allow time for the file dialog to actually open.
        setTimeout ( function () {
                /*-- Since the time it takes for the user to respond
                    to the File dialog can vary radically, use a confirm
                    to keep the File dialog open long enough for the user
                    to act.
                */
                var doClose = confirm ("Close this window?");
                if (doClose) {
                    window.close ();
                }
            },
            444 // 0.444 seconds
        );
    } );
}

function interceptLink (index, node) {
    var jNode   = $(node);
    jNode.click (openInNewTab);
    jNode.addClass ("intercepted");
}

function openInNewTab (zEvent) {
    //-- Optionally adjust the href here, if needed.
    var targURL     = this.href;
    var newTab      = window.open (targURL, "_blank");

    //--- Stop the link from doing anything else.
    zEvent.preventDefault ();
    zEvent.stopPropagation ();
    return false;
}
_
10
Brock Adams

<a>を設定することにより、target="_blank"タグを使用して簡単に行うことができます。

<a href="http://jqueryui.com/resources/download/jquery-ui-1.9.2.custom.Zip" target="_blank">Download</a>​

デモ: http://jsfiddle.net/g5Gn5/

新しいウィンドウ/タブが開き、ファイルダイアログが表示されると自動的に閉じます。

7
Muthu Kumaran

この単純なソリューションを使用するだけです:

<a href="linkToDownloadFile.html" onclick="download('linkToDownloadFile.html'); return false;">

<script>
    function download(link){
      var popout = window.open(link);
      window.setTimeout(function(){
         popout.close();
      }, 2000);
    }
</script>
1
APB