How to select a lot of topics fast?

I’m talking about this moderator’s tool.

I need to move all topics from one category to another now, so do I need to click on each checkbox for this? Or is there a faster way? I hoped there’s Shift+click thing, but nope. :pensive: Maybe there’s another hotkey for this that I don’t know?

4 Likes

In the developer console run

$('input[type="checkbox"]').attr('checked', 'checked')
6 Likes

Damnit … I was JUST about to type

$('input.bulk-select').prop('checked', true);
3 Likes

Well, yea… I will write a jQuery thing probably that will allow to Shift+click. I just hoped this function is already there.

Done. Add this to <head>.

<script type="text/javascript">
$(document).ready(function() {
    if ($('button.btn.bulk-select').length) {
        var shiftOn = false;
        $(document).keydown(function (e) {
            if (e.keyCode == 16) {
                shiftOn = true;
            }
        });
        $(document).keyup(function (e) {
            if (e.keyCode == 16) {
                shiftOn = false;
            }
        });
        
        $(document).on('change', 'input.bulk-select', function() {
            
            if ((shiftOn) && ($('.start-line-bh').length)) {
                // if Shift is on and first checkbox been clicked
                var State = $('.start-line-bh input.bulk-select').prop('checked');
                $('.end-line-bh').removeClass('end-line-bh');
                $(this).parents('tr').addClass('end-line-bh');
                
                $('input.bulk-select').parents('tr').each(function() {
                    if (($(this).hasClass('start-line-bh')) || ($(this).hasClass('end-line-bh'))) {
                        if ($('.i-go-second').length) {
                            $(this).addClass('i-go-first');
                        } else {
                            $(this).addClass('i-go-second');
                        }
                    }
                });
                
            $('.i-go-first').nextUntil($('.i-go-second'), "tr" ).each(function() {
                var Obj = $(this).find('input.bulk-select');
                if (Obj.prop('checked') != State) {
                    Obj.trigger('click').prop('checked', State);
                }
            });
                
                $('.i-go-first, .i-go-second').find('input.bulk-select').prop('checked', State);
                
                $('.i-go-first').removeClass('i-go-first');
                $('.i-go-second').removeClass('i-go-second');
                
            } else {
                // if Shift is off or no checkbox been clicked yet
                $('.start-line-bh').removeClass('start-line-bh');
                $(this).parents('tr').addClass('start-line-bh');
            }
        });
    }

});
</script>

Click on some checkbox, then Shift+click on other. All checkboxes between them will take state of first clicked checkbox.

2 Likes

You need to stop using jQuery ready instead you should use Ember router.

@eviltrout this keeps popping up, can we introduce Discourse.PageReady(function(){}) as a drop-in replacement for jQuery ready ?

2 Likes

Is this answers my other topic? If so, it would be awesome to learn how to do this.
https://meta.discourse.org/t/catch-content-loaded-event-via-js/26323

I feel like if we add that callback we’ll regret it. I know it seems easier to just throw in some jQuery code to update the page but if anyone relies on that it can easily break when we update the ember code underneath.

Giving that hook gives the impression that it is an OK way to do things, when in fact it is hacky.

1 Like

It is hacky. I understand that I will have to fix this code each time you’ll change some HTML around. But I’ll have to deal with it sinse there’s few things that I don’t like about Discourse now, and there’s no other way to fix them. I will probably have to use JS to fix all of this:

https://meta.discourse.org/t/add-new-bbcode-button/25586
https://meta.discourse.org/t/breadcrumbs-with-dropdowns/25205
And maybe this:

Just tried to use my code - didn’t worked. Checkboxes changes state but admin tool still shows I selected only 2 topics. None of this works too:

So I chagned it to send click to checkbox instead - it works this way, but my code glitches now because it triggers itself and as result you can’t select more than 67 topics at once. Will fix it later.

And yea - script breaks somehow after async content been loaded. Although it says $(document).on which means it should catch element even if it’s not on the document when script shoots. Need to find out how to switch from jQuery’s $(document).ready to Ember’s voodoo magic, as @sam said.

Could you not achieve this through the Rails console for now? Should make batch moving topics pretty simple.

Yes, but there are several actions you can do through the bulk topic actions UI, so it would be good to make that easier.

Not true. There is a proper way to extend Discourse rather than raw jQuery and that’s by writing a Discourse plugin. I’d happily point you towards many examples. Using jQuery to write them is a mistake.

This is unfortumately trickier to do because the topic list item has been optimized to use raw handlebars and not ember. Normally you could add all of the topics to the controller.selected array but it doesn’t look like @Sam’s raw’s refactor handles binding that way.

In other words, even if you knew Ember well it would be hard to write this particular feature as a plugin.

1 Like

Okay, please do so. I don’t code Rails yet by I’ll see what I can do.

My refactor still leaves the controller around there is still one view per row so in theory this should still be doable.

Most of our plugins live in the discourse organization on github. I’d suggest looking at. Most are pretty simple and should give you an idea of how we extend discourse. Let me know if you have any questions.

When I looked at it, it didn’t seem to be bound to the selected collection though. They’d have to set up an observer to do that.

I think making Shift+click to select multiple topics would be a great usability enhancement. Gmail, among many other web apps, implements this convenience.

I have used Gmail daily for 10 years and I have never once shift clicked to multiple select. A whole decade. I have used select all, though.

Does this work for others?

I just ran this in my dev console (chrome)

$('input[type="checkbox"]').attr('checked', 'checked')

However, I had to manually check one box for the topic management icon to show up. And then, even though all the topics appeared to be selected, when I tried to bulk set a tag, nothing happened.

Just wondering what the experience of others has been.

If you want to cover a very unusual use case I had, it was hard to select all with a few exceptions in a discourse thread.