Doing it wrong userscripts - Show raw


  • Discourse touched me in a no-no place

    @Onyx said:

    Do you get patch notes in the admin panel? I'd like to see the commit, wonder what they did.

    All we get on the dashboard is the most recent commit's hash. Which only tells us it may, or may not be different to the most recent one we can install. Also a count of how many commits between last update and now.:

    Commits are publicly available at:

    URL: https://github.com/discourse/discourse/commits
    RSS: https://github.com/discourse/discourse/commits/master.atom

    Commit in question:


  • BINNED

    Confirming the weirdness of not working on refresh in Chrome. That's odd. Investigation in progress.

    Also, CSS not getting applied properly to the code icon on toggle. That's a simple one at least.


  • BINNED

    @Onyx said:

    at least some interest

    You have at least one person using it :)


  • BINNED

    @Maciejasjmj said:

    Aside from Chrome still failing to show the button after refresh, only on navigation inside Disco-curse.

    Does anyone know why Chrome has this issue?

    BTW: Thank you @Maciejasjmj and @Onyx for the work on this! I'm liking the "inline raw"!


  • BINNED

    @M_Adams said:

    Does anyone know why Chrome has this issue?

    Same thing on my ancient Opera 12. Assuming it has something to do with the order in which stuff gets loaded. Will investigate today.


  • BINNED

    Well... poop. I tried timing it out, timing out until I'm sure both Ember and Discourse are available, requiring scripts (that at least stopped the debugger from complaining), but it still fails to add elements to the DOM on refresh. I moved it all to document.ready but I still suspect that might (and probably does) trigger before Ember renders all the guff... well, back to inspecting Ember objects I guess.


  • BINNED

    So... update: apparently the code was fine all along, but Discourse URL fuckery messes up the matching rule. Matching the whole site seemingly fixes it.

    Updated code (pretty much just a matching rule change):

    // ==UserScript==
    // @name        TDWTF - Show raw button
    // @namespace   TDWTF
    // @match       http://what.thedailywtf.com/*
    // @description Shows raw form of the post
    // @version     1
    // ==/UserScript==
    
    function getRawPost(e)
    {
        var topicID = e.data.topicID;
        var postID = e.data.postID;
        var callingButton = $(e.target);
    
        // Fuck your inconsistency Discourse! Why don't post numbers match??? Now I have to do this shit...
        var postArea = $('button[data-post-number="' + postID + '"][data-action="share"]') .closest('.contents');
    
        callingButton.toggleClass('active');
    
        if (callingButton.hasClass('active'))
        {
            //Prettify
            callingButton.css({backgroundColor: '#08C', color: '#FFF'});
    
            if (postArea.children('.tdwtf-raw-area') .length == 0 || postArea.children('.tdwtf-raw-area') .html() == '')
            {
                $.get('/raw/' + topicID + '/' + postID) .done(function (content) {
                    if (postArea.children('.tdwtf-raw-area') .length == 0)
                    {
                        postArea.children('.cooked') .after('<pre class="tdwtf-raw-area"></pre>');
                        postArea.children('.cooked') .hide();
                    }
                    postArea.children('.tdwtf-raw-area').css("white-space", "pre-wrap") .text(content);
                    //postArea.children('.tdwtf-raw-area') .html(postArea.children('.tdwtf-raw-area') .text() .replace(/\n/g, '<br>'));
                });
            } 
            else
            {
                postArea.children('.cooked') .hide();
                postArea.children('.tdwtf-raw-area') .show();
            }
        } 
        else
        {
            //Unprettify :(
            callingButton.css({backgroundColor: 'transparent', color: '#A7A7A7'});
    
            postArea.children('.cooked') .show();
            postArea.children('.tdwtf-raw-area') .hide();
        }
    }
    Ember.View.reopen({
        didInsertElement: function () {
            this._super();
            Ember.run.scheduleOnce('afterRender', this, this.insertRawButton);
        },
        insertRawButton: function () {
        }
    });
    Discourse.View.reopen({
        insertRawButton: function () {
            // This thing triggers for any render, so we check if a post has been rendered
            if (this.post) {
                // Get post ID
                var postID = this.post.post_number;
                // Get topic ID
                var topicID = this.post.topic_id;
                // Find action area for the post
                var actionArea = $('button[data-post-number="' + postID + '"][data-action="share"]') .parent('.actions');
                var postArea = actionArea.parents('div.contents') .children('.cooked') [0];
                // This triggers for every render, so we check for existence of the button
                if (actionArea.children('.tdwtf-view-raw') .length == 0) {
                    // Add the button!
                    actionArea.prepend('<button title="view raw post" class="tdwtf-view-raw" data-post-id="' + postID + '"><i class="fa fa-code"></i>#' + topicID + ':' + postID + '</button>') .children('.tdwtf-view-raw') .on('click', {
                        topicID: topicID,
                        postID: postID
                    }, getRawPost);
                }
            }
        }
    });
    

    I think some styling errors still happen in Chrome but too tired to play with it atm.



  • This is really nice - wish I had found it earlier.

    I wrote a quick & dirty bookmarklet that does kind of the same thing for my phone (which doesn't natively have a way to implement userscripts). The downside is it doesn't respond to post loading (you have to run the bookmarklet again), but it works for what I need it for:

    javascript:(function(a){var c=a("#topic").attr("data-topic-id");a("div.contents:not(.rawified)").each(function(){var b=a(this).find('button[data-action="share"]').attr("data-post-number"),d='<button class="fa fa-code view-raw" data-url="'+("/raw/"+c+"/"+b)+'" data-post-number="'+b+'"></button>';a(this).addClass("rawified").find("div.actions").prepend(d);a('button.view-raw[data-post-number="'+b+'"]').click(function(b){b='<iframe src="'+a(this).attr("data-url")+'" style="width: 100%; border: 1px solid #ccc;"></iframe>'; a(this).closest("div.contents").after(b)})})})(jQuery);
    

Log in to reply