Yes it is a bit tricky indeed.
I'm not sure my solution is the best approach but it works and survives page reloads. You could probably do it by pure javascript without any callbacks to the server as well.
First in your ListViewColumn implementation add a "javascript bindable" method, something like
@JavaScriptMethod
public void mark(String fullName, boolean checked) {
Set<String> marked = getMarkedSet();
if (marked != null) {
if(checked) {
marked.add(fullName);
} else {
marked.remove(fullName);
}
}
}
getMarkedSet() would get it from the user's HttpSession by Stapler.getCurrentRequest().getSession(true) a special Set for this particular view instance.
make a columnHeader.groovy (or .jelly if you are so inclined) for your ListViewColumn
def st = namespace("jelly:stapler")
th(tooltip: _("tooltip"), _("Check"))
st.bind(var: "myItemSelector", value: my)
And in column.groovy (or .jelly) you can then call the bound java proxy set in the header.
def f = namespace(lib.FormTagLib)
td {
f.checkbox(checked: my.isMarked(job.fullName), onclick: "myItemSelector.mark('${job.fullName}', this.checked)")
}