<?xml version="1.0"?>
<!--
/* ***** BEGIN LICENSE BLOCK *****
 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
 *
 * The contents of this file are subject to the Mozilla Public License Version
 * 1.1 (the "License"); you may not use this file except in compliance with
 * the License. You may obtain a copy of the License at
 * http://www.mozilla.org/MPL/
 *
 * Software distributed under the License is distributed on an "AS IS" basis,
 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
 * for the specific language governing rights and limitations under the
 * License.
 *
 * The Original Code is Windows Download Taskbar Progress.
 *
 * The Initial Developer of the Original Code is
 * the Mozilla Foundation.
 * Portions created by the Initial Developer are Copyright (C) 2010
 * the Initial Developer. All Rights Reserved.
 *
 * Contributor(s):
 *   Felipe Gomes <felipc@gmail.com>
 *
 * Alternatively, the contents of this file may be used under the terms of
 * either the GNU General Public License Version 2 or later (the "GPL"), or
 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
 * in which case the provisions of the GPL or the LGPL are applicable instead
 * of those above. If you wish to allow use of your version of this file only
 * under the terms of either the GPL or the LGPL, and not to allow others to
 * use your version of this file under the terms of the MPL, indicate your
 * decision by deleting the provisions above and replace them with the notice
 * and other provisions required by the GPL or the LGPL. If you do not delete
 * the provisions above, a recipient may use your version of this file under
 * the terms of any one of the MPL, the GPL or the LGPL.
 *
 * ***** END LICENSE BLOCK ***** */

/**
 * This tests that the Windows 7 Taskbar Progress is correctly updated when
 * the download state changes.
 */
-->

<window title="Win7 Taskbar Progress"
        xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
        onload="test();">

  <script type="application/javascript"
          src="chrome://mochikit/content/MochiKit/packed.js"/>
  <script type="application/javascript"
          src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"/>
  <script type="application/javascript"
          src="chrome://mochikit/content/tests/SimpleTest/EventUtils.js"/>
  <script type="application/javascript"
          src="utils.js"/>

  <script type="application/javascript">
  <![CDATA[

const kTaskbarID = "@mozilla.org/windows-taskbar;1";
const DOWNLOAD_MANAGER_URL = "chrome://mozapps/content/downloads/downloads.xul";
const DLMGR_UI_DONE = "download-manager-ui-done";

const Cu = Components.utils;
const nsITP = Ci.nsITaskbarProgress;

let DownloadTaskbarProgress, dm;
let downloadA, downloadB, gGen;

let testState = {
  activeDownloadCount: 0,
  pausedDownloadCount: 0,
  finishedDownloadCount: 0,

  regularStateTested: false,
  pausedStateTested: false,
  noDownloadsStateTested: false
}

function continueTest() {
  SimpleTest.executeSoon(function(){
    gGen.next();
  });
}

let wasPaused = {};

let downloadListener = {

  onStateChange: function(a, b, c, d, e) {
    checkCorrectState();
  },

  onDownloadStateChange: function(aState, aDownload)
  {

    if (aDownload.state == Ci.nsIDownloadManager.DOWNLOAD_PAUSED) {
      wasPaused[aDownload.id] = true;
      testState.pausedDownloadCount++;
      testState.activeDownloadCount--;

      continueTest();
    }

    if (aDownload.state == Ci.nsIDownloadManager.DOWNLOAD_FINISHED) {
      testState.activeDownloadCount--;
      testState.finishedDownloadCount++;
      aDownload.targetFile.remove(false);

      SimpleTest.executeSoon(checkCorrectState);
      if(testState.finishedDownloadCount == 2) {
        SimpleTest.executeSoon(finishTest);
      }

    }

    if (aDownload.state == Ci.nsIDownloadManager.DOWNLOAD_DOWNLOADING) {
      if (!wasPaused[aDownload.id])
        dm.pauseDownload(aDownload.id);
      continueTest();
    }

  },

  onProgressChange: function(a, b, c, d, e, f, g) { },
  onSecurityChange: function(a, b, c, d) { }
};

function testSteps() {

  // Step 1 - Add downloads and pause

  testState.activeDownloadCount++;
  downloadA = addDownload();
  yield; // added
  yield; // paused

  testState.activeDownloadCount++;
  downloadB = addDownload();
  yield; // added
  yield; // paused

  // Step 2 - Resume downloads
 
  testState.activeDownloadCount++;
  testState.pausedDownloadCount--;
  dm.resumeDownload(downloadA.id);
  yield; 

  testState.activeDownloadCount++;
  testState.pausedDownloadCount--;
  dm.resumeDownload(downloadB.id);
  yield;

  yield;
}

function finishTest() {
  ok(testState.regularStateTested, "Tests went through regular download state");
  ok(testState.pausedStateTested, "Tests went through paused download state");
  ok(testState.noDownloadsStateTested, "Tests went through finished downloads state");
  dm.removeListener(downloadListener);
  gGen.close();
  SimpleTest.finish();
}

function checkCorrectState() {

  if(testState.activeDownloadCount < 0 || testState.pausedDownloadCount < 0) {
    ok(false, "There shouldn't be negative download counts");
    SimpleTest.finish();
  }

  let taskbarState = DownloadTaskbarProgress.taskbarState;

  if (testState.activeDownloadCount) {
    //There's at least one active download
    ok(taskbarState == nsITP.STATE_NORMAL || taskbarState == nsITP.STATE_INDETERMINATE, "Correct downloading state");
    testState.regularStateTested = true;
  } else if (testState.pausedDownloadCount) {
    //There are no active downloads but there are paused ones
    ok(taskbarState == nsITP.STATE_PAUSED, "Correct paused state");
    testState.pausedStateTested = true;
  } else {
    //No more downloads
    ok(taskbarState == nsITP.STATE_NO_PROGRESS, "Correct finished downloads state");
    testState.noDownloadsStateTested = true;
  }

}

function test() {
  testSetup();
}

function testSetup()
{
  //Test setup
  let dmui = getDMUI();
  if (!dmui) {
    todo(false, "skip test for toolkit download manager UI");
    return;
  }

  let isWin7OrHigher = false;
  try {
    let version = Cc["@mozilla.org/system-info;1"]
                    .getService(Ci.nsIPropertyBag2)
                    .getProperty("version");
    isWin7OrHigher = (parseFloat(version) >= 6.1);
  } catch (ex) { }

  if (!isWin7OrHigher) {
    return;
  }

  let tempScope = {};
  Cu.import("resource://gre/modules/DownloadTaskbarProgress.jsm", tempScope);
  Cu.import("resource://gre/modules/Services.jsm");

  DownloadTaskbarProgress = tempScope.DownloadTaskbarProgress;
  let TaskbarService =  Cc[kTaskbarID].getService(Ci.nsIWinTaskbar);

  isnot(DownloadTaskbarProgress, null, "Download taskbar progress service exists");
  is(TaskbarService.available, true, "Taskbar Service is available");

  dm = Cc["@mozilla.org/download-manager;1"].
           getService(Ci.nsIDownloadManager);

  // First, we clear out the database
  dm.DBConnection.executeSimpleSQL("DELETE FROM moz_downloads");

  // See if the DM is already open, and if it is, close it!
  let win = Services.wm.getMostRecentWindow("Download:Manager");
  if (win) {
    win.close();
  }
  let os = Services.obs;
  const DLMGR_UI_DONE = "download-manager-ui-done";

  gGen = testSteps();
  dm.addListener(downloadListener);

  let testObs = {
    observe: function(aSubject, aTopic, aData)
    {
      if (aTopic != DLMGR_UI_DONE) {
        return;
      }
      os.removeObserver(testObs, DLMGR_UI_DONE);
      continueTest();
    }
  };

  // Register with the observer service
  os.addObserver(testObs, DLMGR_UI_DONE, false);

  // Show the Download Manager UI
  dmui.show();

  SimpleTest.waitForExplicitFinish();
}

  ]]>
  </script>

  <body xmlns="http://www.w3.org/1999/xhtml">
    <p id="display"></p>
    <div id="content" style="display:none;"></div>
    <pre id="test"></pre>
  </body>
</window>
