// ==UserScript==
// @name          Fix Audible
// @namespace     http://roub.net/
// @description   Replaces audible.com javascript: links with usable, tab-able hrefs.  adds permalinks. (Paul Roub, v1.4)
// @include       http://audible.com/*
// @include       http://www.audible.com/*
// ==/UserScript==
//
// History: http://roub.net/xul/greasemonkey/audible.history.txt
//


function varWithDefault(varname, defval)
{
    if (typeof(window[varname]) != 'undefined')
    {
        return(window[varname]);
    }

    if ((typeof(window._content) != 'undefined') && (typeof(window._content[varname]) != 'undefined'))
    {
        return(window._content[varname]);
    }

    if (eval("typeof(" + varname + ")") != 'undefined')
    {
        return(eval(varname));
    }

    return(defval);
}


function fixAudEscapeString(st)
{
    var result = st.replace(/'/g, "\\'");
    result = result.replace(/"/g, "\\\"");

    return(result);
}


(function() {
    //  if we're an amazon-linked page, jump through to the regular page.
    //
    var locRegEx = new RegExp("amazonProduct\\.jsp.*\\?");

    if (locRegEx.exec(document.location.href))
    {
        var lns = document.evaluate("//a[contains(@href,'store/product.jsp')]", document, null, XPathResult.FIRST_ORDERED_NODE_TYPE, null);

        if (lns)
        {
            var node = lns.singleNodeValue;

            if (node && node.href)
            {
                document.location.href = node.href;
                return;
            }
        }
    }


    var i;

     var oneReg = new RegExp("javascript:linkThis[a-zA-Z]*\\([ \t]*['\"](.*)['\"][ \t]*\\)");
     var twoReg = new RegExp("javascript:linkThis[a-zA-Z]*\\([ \t]*['\"](.*)['\"][ \t]*,[ \t]*['\"](.*)['\"][ \t]*\\)");
     var shareRegEx = new RegExp("shareThis.*ProductID=(.+?)[\\&'\\\"]");

     var    ourLinkString = '';

     var    sesPat = new RegExp('BV_SessionID=([^\\&]+)');
     var    engPat = new RegExp('BV_EngineID=([^\\&]+)');
     var    ourLinkUrl = varWithDefault('link_url', '');

     var    sm = sesPat.exec(window.location.search);

     if (sm == null)
     {
         sm = sesPat.exec(ourLinkUrl);
     }

     if (sm != null)
     {
         ourLinkString = 'BV_SessionID=' + sm[1];
     }

     var    em = engPat.exec(window.location.search);

     if (em == null)
     {
         em = engPat.exec(ourLinkUrl);
     }

     if (em != null)
     {
         ourLinkString = ourLinkString + '&BV_EngineID=' + em[1];
     }


     var    theServer = varWithDefault('the_myserver', 'http://www.audible.com')
     var    theSecureServer = varWithDefault('the_mysecureserver', 'https://www.audible.com')
     var    listeningPreference = varWithDefault('myListeningPreference', 'none');
     var    linkString = varWithDefault('the_linkstring', ourLinkString);
     var    cgiInfo = varWithDefault('the_cgiinfo', '/adbl');
     var    theUniqueKey = varWithDefault('uniqueKey', '');


     for (i = 0; i < document.links.length; ++i )
     {
         var     ln = document.links[i];
         var	href = ln.href;
         var a = "";
         var b = "";

         var m = twoReg.exec(href);

         if (m == null)
         {
             m = oneReg.exec(href);
         }

         if (m != null)
         {
             if (m.length > 2)
             {
                 a = m[1];
                 b = m[2];
             }
             else
             {
                 a = m[1];
             }

             var isSecure = href.indexOf('linkThisSecure') >= 0;
             var server = theServer;

             if (isSecure)
             {
                 server = theSecureServer;
             }

             //  the link-manipulation lines below are barely-modified copies of audible's publically-viewable
             //  javascript.  copyrighted by them.  i really don't want credit for any of this.
             //
	     var d = '';

             if(listeningPreference != 'none')
                 d = '&setListeningPref='+listeningPreference;

             if (a == '/store/product.jsp')
             {
                 if ('category.jsp' == 'subcategory.jsp')
                     b += '&parentCat=';
                 else if ('category.jsp' == 'category.jsp')
                     b += '&parentCat=Arts+and+Entertainment';
             }

             if(a == '/store/freestuff.jsp')
             {
                 a='/store/freeStuff.jsp';
                 b='&Type=freeStuff1';
             }

             if((a.indexOf('/store/mySamplePreferences.jsp') >= 0) && (b.indexOf('smplCnt=') >= 0))
             {
                 continue;
             }

             var newhref = server + cgiInfo + a + '?' + linkString + '&uniqueKey=' + theUniqueKey+b+d;

             ln.href = newhref;
         }


         //     if we find a 'share this page' link, follow it with an amazon-based permalink
         //
         m = shareRegEx.exec(href);

         if (m && (m.length == 2))
         {
             var productId = m[1];

	     var permRef = "http://www.audible.com/adbl/store/welcome.jsp?entryRedirect=/store/sharedTitle.jsp&entryParams=^ProductID~" + productId;

             var bookTitle = 'audible.com audiobook';

             var imgs = document.evaluate("//img[contains(@src,'full_image.jpg')]", document, null, XPathResult.FIRST_ORDERED_NODE_TYPE, null);

             if (imgs && imgs.singleNodeValue)
             {
                 var    alt = imgs.singleNodeValue.alt

                 if (alt && (alt.length > 0))
                 {
                     bookTitle = 'audible.com: ' + fixAudEscapeString(alt);
                 }
             }

             var permJs = false;

             if (window.sidebar && window.sidebar.addPanel)
             {
                 permJs = "window.sidebar.addPanel('" + bookTitle + "','" + permRef + "',''); return false;";
             }

             var linkImg = "http://img.audible.com/images/common/icons/arrow_orange.gif";

             var linkText = "bookmark this page";

             if (! permJs)
             {
                 linkText = "permalink";
             }

             var linkStyle = 'font-weight: bold; font-variant: small-caps;';
             var linkTitle = 'Bookmarkable link to this product';
             var imgStyle = 'border: none; padding-top: 8px;'

             var newLink = document.createElement('a');

             newLink.setAttribute('href', permRef);    
             newLink.setAttribute('title', linkTitle);
             newLink.setAttribute('style', linkStyle);

             if (permJs)
             {
                 newLink.setAttribute('onclick', permJs);
             }

             newLink.innerHTML = "<img src='" + linkImg + "' alt='" + linkTitle + "' style='" + imgStyle + "'/> " +
                 linkText;

             var newBreak = document.createElement('br');

             var parent = ln.parentNode;

             parent.appendChild(newLink);
             parent.appendChild(newBreak);
         }
     }
})();
