User:Odie5533/F2ComButton/f2com button.user.js

Note: After saving, you have to bypass your browser's cache to see the changes. Internet Explorer: press Ctrl-F5, Mozilla: hold down Shift while clicking Reload (or press Ctrl-Shift-R), Opera/Konqueror: press F5, Safari: hold down Shift + Alt while clicking Reload, Chrome: hold down Shift while clicking Reload.
// <pre><nowiki>
/*
F2ComButton (C) 2009-2012 Odie5533
This program is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 2 of the License, or (at your
option) any later version.

This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
Public License for more details.

You should have received a copy of the GNU General Public License along
with this program; if not, write to the Free Software Foundation, Inc.,
59 Temple Place, Suite 330, Boston, MA 02111-1307 USA


Some stuff taken from http://userscripts.org/scripts/review/2012
   --> (Link Original Image - (c) 2005-2009 Johannes la Poutre)
*/
// ==UserScript==
// @name           F2Com Button
// @namespace      http://flickr.com/*
// @include        http://www.flickr.com/*
// ==/UserScript==
// window.content.wrappedJSObject = unsafeWindow // note to self

/* Changelog
2012-12-01 Updated to use author's username if they have not set their real name
*/

var ImgDesc = {
    // Set to your TUSC username
    tusc_username: 'Odie5533', // CHANGE THIS - your username is not Odie5533...
    tusc_password: '',

    // url of the current image being viewed
    imgurl: "",
    // extension of the current image being viewed
    extension: "",
    license: "",
    date: "",
    // filename to upload to on the common
    filename: "",
    // description to give on the commons
    description: "",
    coords: "",
    authorpage: "",
    imagepage: "",
    recvsize: false,
    recvauth: false,
    
    // myLog is used for debug purposes
    myLog: function(strng) {
        //GM_log(strng);
    },
    
    // The init function is run when a user first loads the page
    init: function() {
        // First determine if the image is Creative Commons
        this.license = this.detectLicense();
        this.myLog("License tag: " + this.license);
        // if no valid license is found
        if (!this.license)
            return true;
            
        // At the top of the page is some meta information that we can parse
        // title of the image:
        var meta_title = document.evaluate("//meta[@property='og:title']",
                      document, null, XPathResult.ANY_TYPE, null).iterateNext();
        this.title = meta_title.getAttribute('content');
        this.myLog("Image title: " + this.title);

        // The pid is a unique number that identifies the image:
        var meta_url = document.evaluate("//meta[@property='og:url']", document,
                                null, XPathResult.ANY_TYPE, null).iterateNext();
        var reg_pid = /.*\/(\d+)/g;
        var pid_matches = reg_pid.exec(meta_url.getAttribute('content'));
        this.pid = pid_matches[1];
        this.myLog("pid: " + this.pid);
        
        // image owner's nsid
        var p = document.evaluate("//div[@id='photo-story-attribution']/p",
                      document, null, XPathResult.ANY_TYPE, null).iterateNext();
        this.nsid = p.getAttribute('nsid');
        this.myLog("nsid: " + this.nsid);
        
        this.author = document.evaluate("//span[@class='photo_navi_contact']/a",
                     document, null, XPathResult.STRING_TYPE, null).stringValue;
        this.author = this.author.replace(/^\s+|\s+$/g, ''); // trim author name
        if (this.author == "No real name given") {
            this.author = document.evaluate("//strong[@class='username']/a",
                     document, null, XPathResult.STRING_TYPE, null).stringValue;
        }
        this.myLog("Author: " + this.author);
        
        // Parses the image's actual url so we can determine the extension
        var meta_img = document.evaluate("//meta[@property='og:image']",
                      document, null, XPathResult.ANY_TYPE, null).iterateNext();
        this.imgurl = meta_img.getAttribute('content');
        this.myLog("Image url: " + this.imgurl);

        // parses the geo coords (in the form lat|long)
        this.coords = this.parseGeo();
        
        // constructs needed info for upload
        this.authorpage = "http://www.flickr.com/people/" + this.nsid;
        this.imagepage = "http://www.flickr.com/photos/" + this.nsid + "/" + this.pid + "/";
        this.extension = this.imgurl.match(/.*\.(\w+)($|\?)/)[1];
        this.filename = escape(this.title.replace("'","&#38")) + '.' + this.extension;

        var pDesc = document.getElementById('description_div');
        if (pDesc) {
            var pDesc = pDesc.innerHTML.replace('#','').replace('&nbsp;',' ');
            pDesc = pDesc.replace(/<a[^>]+href="([^"]+)"[^>]+?>(.*?)<\/a>/gi,'[$1 $2]'); // change anchors to wiki style
            pDesc = pDesc.replace(/<\/?strong>/gi, "'''"); // bold support
            pDesc = pDesc.replace(/\n/gi,''); // delete new lines
            pDesc = pDesc.replace(/(.*)<\/p>/i, '$1'); // delete </p> from the end
            pDesc = pDesc.replace(/<p>/gi,'').replace(/<\/p>/gi,'\n\n'); // Replace paragraphs with breaks
            this.description = 'The following is the author\'s description of the photograph quoted directly from the photograph\'s Flickr page.\n\n"' + pDesc + '"';
        }
        // adds the upload button the Flickr page
        this.addUploadButton();
        return false;
    },
    
    assembleUrl: function() {
        var uploadDesc = '{{Information\n|Description='+this.description+"\n|Source=originally posted to '''[[Flickr]]''' as ["+
                         this.imagepage+' '+this.title+']\n* Uploaded using [[User:Odie5533/F2ComButton|F2ComButton]]\n|Date='+this.date+
                         '\n|Author=['+this.authorpage+' '+this.author+
                         ']\n|Permission='+this.license+'{{Flickrreview}}\n|other_versions=\n}}';
        if (this.coords != "") {
            uploadDesc += '\n{{Location dec|'+this.coords+'}}';
        }

        return commonsUrl = 'http://commons.wikimedia.org/w/index.php?title=Special:Upload&uploadformstyle=basic&wpDestFile='+
                         this.filename+'&wpUploadDescription=' + escape(uploadDesc);
    },
    
    detectLicense: function() {
        var lic = this.parseAnchors();
        if (!lic)
            lic = this.parseImages();
        lic = this.parseSpecialTags(lic);
        return lic;
    },
    
    parseImages: function() {
        var images = document.getElementsByTagName('img');
        for (var i = 0; i < images.length; i++) {
            var img = images[i];
            if (img.src == "http://l.yimg.com/g/images/spaceout.gif" && img.alt == "No known copyright restrictions" && img.className == "f-sprite fs-icon_no_known_restrictions")
                return '{{Flickr-no known copyright restrictions}}';
        }
        return null;
    },
    
    // Searches the page for the image's license and returns it if found
    parseAnchors: function() {
        var anchors = document.getElementsByTagName('a');
        for (var i = 0; i < anchors.length; i++) {
            if (this.date == "" && anchors[i].href.indexOf('date-posted') != -1) {
                this.date = anchors[i].innerHTML;
            }
            if (anchors[i].href.indexOf('date-taken') != -1) {
                this.date = anchors[i].innerHTML;
            }
            if (anchors[i].rel == "license cc:license") {
                if (anchors[i].href == 'http://creativecommons.org/licenses/by-sa/2.0/deed.en') {
                    return '{{cc-by-sa-2.0}}';
                }
                if (anchors[i].href == 'http://creativecommons.org/licenses/by/2.0/deed.en') {
                    return '{{cc-by-2.0}}';
                }
            }
        }
        return null;
    },
    
    parseSpecialTags: function(lic) {
        //Powerhouse Museum
        if (this.nsid == '24785917@N03') {
            if (lic == '{{Flickr-no known copyright restrictions}}')
                lic = '{{PD-Australia}}';
            return '{{Flickr-Powerhouse-Museum-image}}' + lic; //prepend template
        } else if (this.nsid == '83979593@N00') {
            //Brooklyn Museum
            return '{{Flickr-Brooklyn-Museum-image}}' + lic;
        } else if (this.nsid == '29454428@N08') {
            if (lic == '{{Flickr-no known copyright restrictions}}')
                return '{{PD-Australia}}';
        }
        return lic;
    },
    
    // returns coords in form lat|long
    parseGeo: function() {
        var metas = document.getElementsByTagName('meta');
        for (var i = 0; i < metas.length; i++) {
            if (metas[i].name == 'geo.position') {
                return metas[i].content.replace("; ", "|");
            }
        }
        return "";
    },
    
    addUploadButton: function() {
        this.f2div = document.createElement('div');
        this.f2div.id = 'F2ComButton';
        var sidebar = document.getElementById('sidebar');
        sidebar.insertBefore(this.f2div, sidebar.childNodes[0]);
    
        var comButton = document.createElement('a');
        comButton.innerHTML = 'Upload to Commons &#8679;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;';
        comButton.href = "javascript:f2com_load();";
        var magnusButton = document.createElement('a');
        magnusButton.innerHTML = 'MagnusTool &#8680;';
        magnusButton.href = "javascript:void(window.open('http://toolserver.org/~magnus/flickr2commons.php?tusc_user="+
                            this.tusc_username + "&tusc_password=" + this.tusc_password +
                            "&flickr_url=" + this.imagepage + "'));";
        
        this.f2div.appendChild(comButton);
        this.f2div.appendChild(magnusButton);
    }
};

ImgDesc.init();

// Called when the Upload to Commons button is clicked
unsafeWindow.f2com_load = function() {
    // The following code is no longer needed because Flickr now includes
    // the user's real name on the photo page
    /*if (!ImgDesc.recvauth) {
        ImgDesc.recvauth = true;
        lookup(ImgDesc.authorpage, loadedFlickrUserPage);
    } else {
        window.open(ImgDesc.assembleUrl());
    }*/
    window.open(ImgDesc.assembleUrl());
    // Finds the link to the original size image so that it can be downloaded
    if (!ImgDesc.recvsize) {
        ImgDesc.recvsize = true;
        //lookup("http://www.flickr.com/photo_zoom.gne?id="+ImgDesc.pid+"&size=o", loadedSizePage);
        lookup("http://www.flickr.com/photos/"+ImgDesc.nsid+"/"+ImgDesc.pid+"/sizes/o/", loadedSizePage);
    }
}

function loadedSizePage(res) {
    var re = new RegExp('<img src="([^"]+static[^"]+' + ImgDesc.pid + '[^"]+)"');
    var m = res.responseText.match(re);
    if (m) {
        var imglink = "";
        // Check whether we can download the original size
        var orig = new RegExp('_o');
        if (m[1].match(orig)) {
            imglink = m[1].replace('_o','_o_d');
        } else {
            imglink = m[1].replace('.jpg','_b.jpg');
        }
        // Create a button link to the largest size
        var dlButton = document.createElement('a');
        dlButton.innerHTML = 'Download original &#8681;';
        dlButton.href = imglink;
        
        var br = document.createElement('br');
        var f2div = document.getElementById('F2ComButton');
        f2div.appendChild(br);
        f2div.appendChild(dlButton);
    }
}

/* Not currently used
function loadedFlickrUserPage(res) {
    var re = new RegExp(/<span class="RealName">(.*)/);
    var m = res.responseText.match(re);
    if (m) {
        m = m[1].replace(/<[^>]+>/g, '');
        if (m) {
            m = m.match(/[\/\s]+(.*?)\s*(&nbsp;)?\s*$/)[1];
            ImgDesc.author = m;
        }
    }
    if (ImgDesc.author == "") {
        var m = res.responseText.match(/<span class="nickname">(.*?)<\/span>/);
        if (m) {
            ImgDesc.author = m[1];
        }
    }
    alert(ImgDesc.author);
    window.open(ImgDesc.assembleUrl());
}*/

function lookup(url, onload) {
    if (url.match(/^http:\/\/(\w+\.)*?flickr\.com\/.+/)) {
        window.setTimeout(_wrappedLookup, 0, url, onload);
    } else {
      myLog('lookup: security breach with url ' + url);
    }
}

function _wrappedLookup(url, onload) {
    try {
        GM_xmlhttpRequest({
            method: 'GET',
            url: url,
            headers: { Referer: 'http://www.flickr.com/photos/' },
            onload: onload
        });
    } catch (e) {
        myLog('_wrappedLookup: ' + e);
    }
}
// </nowiki></pre>