Skip to main content
Kinetic Community

Arranging Checkbox Answers in Multiple Columns

Overview

This solution article explains how to collect the answers in a multiple-checkbox List field and arrange them in parallel columns using JavaScript.

Problem

When you have a large number of checkboxes related to a single question, their arrangement on the page can become unwieldy and ugly.

Horizontal Arrangement

Horizontal Checkbox Arrangement

In horizontal mode, the selections in subsequent rows do not line up. In fact, you may even find some checkboxes at the right-hand margin have been separated from their labels.

 

Vertical Arrangement

Vertical Checkbox Arrangement

Vertical mode is only slightly better. Unfortunately, you may have to scroll down just to see all of your options.

 

Background

To approach this problem and find a viable solution, we need to understand how the answer elements are placed on the rendered page in a Service Item.

Here's what the page looks like in Firebug:

HTML -- Checkbox Answer Layout

As you can see, the questionLayer contains the questionLabel and the questionAnswer. And under the questionAnswer element, we have as many answerCheckbox elements as the question needs. The solution to our problem will be to wrap the answerCheckbox items in separate divs, with each successive div floating next to the first (i.e, "float:left").

The JavaScript Code

<script type='text/javascript'>
// Assemble multiple checkboxes in an answer evenly in columns.
function columnizeCheckboxes(labelName, requestedColumns, columnWidth) {
    "use strict";
    // Find the element.
    var selectorString  = "div[class~=\"questionAnswer\"]";
    selectorString += "[label=\"" + labelName + "\"]";
    var parentElement = $(selectorString);

    // Create a <div> string to contain the checkboxes.
    var divString = '<div style=\"float:left; width: ';
    divString += columnWidth + 'px;\"></div>';
    var wrapperDiv = $(divString);
   
    var answerCheckboxes = parentElement.children();
    var totalCheckboxes = answerCheckboxes.size();
    var checkboxesPerColumn = Math.ceil(totalCheckboxes / requestedColumns);

    // Loop over the columns in a given chunk and apply the div.
    var builtColumns = 1;
    for (var i = 0; builtColumns < requestedColumns; i += checkboxesPerColumn) {
        var elem = null;
        elem = answerCheckboxes.slice(i, i + checkboxesPerColumn);
        elem.wrapAll(wrapperDiv);
        builtColumns++;
    }
}
</script>

We can add this function to the CustomHeaderContent field on our Pizza Test Service Item and test it in Firebug's JavaScript console. The function takes three arguments:

  1. The label of the overall question field.
  2. The number of columns we want the checkboxes to fit in.
  3. The width in pixels for each column.
Note:  We'll start with the checkboxes arranged in a single vertical column.

Suppose we want to arrange our 23 topping selections in 5 columns, where each column is 100 pixels wide. We can test it out on the console, like this:

Testing the Function on the Console

Just press <Enter>, and the function executes. And the result looks like this:

Toppings Arranged in Five Columns

Applying the Solution

We need to call the function on the page where the checkbox List question appears. Since the function call needs to occur on page load, we'll add it as a Page Event.

This time, we'll set it for three columns, where each has a width of 150 pixels.

Columnizing Checkboxes on Page Load

 

Naturally, in this case we use single quotes around our question label. Now when we open the Pizza Test Service Item, the checkboxes sort themselves neatly into 3 columns of equal width:

Toppings Arranged in Three Columns

 

And we're done!

Addendum

Actually, we're not quite done. It turns out that this code can disrupt the normal behavior of a review page, so we'll want to add another page load event that explicitly disables the fields when in review mode.

Disable Checkboxes in Review

 

That line of JQuery code sets the 'disabled' attribute to true on every existing checkbox on the page.

$('input[type=\"checkbox\"]').attr('disabled', true);
Note:  Many thanks to Andre, who wrote the original version the "columnizer" code.

 

Related

Topics
Custom Event
Replace Simple Data Requests with Bridging
Custom Event
Replace Simple Data Requests with Bridging
Enabling and Disabling Options for a Radio Button or Checkbox List Question
Sometimes you may desire to show someone a radio button or checkbox question but not allow them to choose from all the options. This solution describes how to use JQuery to accomplish that.
How to set up a bridge to a Kinetic Core Submissions for one of your Forms
This article includes the details of to set up a bridge to Kinetic Core Submissions to one of your Forms.
Remove Spaces
How to remove white space from answers.
Retrieve an Answer
Say you have a question on the page named 'First Name', and you need to retrieve the answer of this question to use within a custom javascript event.
Javascript documentation
Many of the functions contained here are called automatically when creating events within one of the Author consoles. However, there are situations where a customer may want to write custom javascript to perform a task beyond the capabilities of the events/actions provided. The information in these documents should assist developers in those scenarios.
Javascript documentation
Many of the functions contained here are called automatically when creating events within one of the Author consoles. However, there are situations where a customer may want to write custom javascript to perform a task beyond the capabilities of the events/actions provided. The information in these documents should assist developers in those scenarios.
Custom Event
Replace Simple Data Requests with Bridging
Custom Event
Replace Simple Data Requests with Bridging
Check Box Events - Insert and Remove
How to use the Insert and Remove Events when using a Check Box Question.
Remove a Checkbox Answer
How to Remove or Disable one of the Answers from your Check box list Question.
Drop Down Search
Javascript file allowing filtering/searching of Kinetic Request drop down fields based on css class.
Notifie JS
Javascript library for displaying notifications
Chrome Developer Tools
Chrome Developer Tools are included in the Chrome web browser. Similar to Firebug, Chrome allows web developers and programmers deep access into the internals of the browser and their web application.
Firebug
Firebug is an open source add-on that integrates with Firefox to provide development and debugging tools. You can edit, debug, and monitor CSS, HTML, and JavaScript live in any web page.
A nicer Alert option
Very often you need to display an error to the user. In these times we tend to use the alert(...) javascript function, which is nice and easy but a little on the ugly side. The Kinetic utility javascript code allows for a better approach, giving a nicer looking alert popup with some better features added, and of course is very easy to call/use.
Add a button next to submit
There are occasions where users wish to add a button to the bottom of a request next to the "Submit" button.  This is usually a Cancel button but can be any button. If the button were any place else in the Request the solution would be as simple as just adding a text question with html for a button. Since the "Submit" button is outside the div which contains the questions, the solution requires a different solution.
Cascading Menus
There can be a need to make one menu drive another that drives another. This can be done with Simple Data Requests or with Bridging.
Checkbox in Columns - Using jQuery
This Service Item uses jQuery along with JavaScript to put Checkbox Elements into multiple columns.
Combine two menus
This is an example of combining menu options from two menus into one menu.  The combine menu is sorted and duplicates are removed from the list.
Copy menu options
At times, there is a need to use javascript to copy the menu values from one menu to another menu.  This sample function will to that.
Cost Calculations
At times Service Items require the calculation of a total cost based upon the items selected.  Ordering computer accessories is an example of this scenario.  The user can select from several different computer accessories, each of which has an associated cost.
Creating Conditional Answer Validation
There can be a need for two different validations on a field, based on other answers in the service item. In this case you cannot use the built-in validation system and must handle the validation separately.
Creating List Options based on Table Contents
It may be desired to create list options from a data table in the item.
Debugging - YAHOO.lang.dump
Design and Style Guide
Dynamically Show and Hide Individual Checkboxes in a Single Checkbox Question
There is a possibility that you may want to control which options a user selects based on something already selected (either on an earlier page or above on the current page). This solution describes how to have one checkbox questions with all the options and control which options the user sees by showing/hiding individual checkboxes.
Enabling and Disabling Options for a Radio Button List Question
Sometimes you may desire to show someone a radio button question but not allow them to choose from all the options. This solution describes how to use JQuery to accomplish that.
Get parameters from the URL
Sometimes it is useful  to included parameters(values) in the URL.  This allows the Service Item to be opened while passing values into it.  These values can be used by logic upon opening of the Service Item.  For example you may want to pre-populate a question with a value.  You can pass a parameter in the URL for the Service Item and the value can be used immediately.
How to prevent page submission on error of a beforeSubmit event
When using custom events on the beforeSubmit action of a page, it is often advantageous to add a "catch all" for potential errors and to prevent the page from submitting. For example, if I have a custom event on beforeSubmit that copies multiple elements from the page and stores them in a hidden answer field, and that event errors, I don't want to page to submit (indicating to the user that the request was successful) with a blank answer field.
How to use JS instead of Events
There can be cases where managing a set of events gets unwieldy. In this example, there are a series of events that are necessary to insert/remove, require/make optional, set read only/read-write, and set fields internal for a combination of two radio buttons. That would be 48 events or one javascript function and two events.
Long Default Text
The Default Answer field on the Defaults tab of the Question only allows for input of 255 characters (in versions before 5.1), but you may want to set a larger default for a text field.
Making your table scrolling, paginated, or sortable
There are various places within your service item you may be using YUI datatables: to adjust the display of the data returned from a simple data request or a bridging request, to store a table of items your customer is requesting, etc. Occassionally it is desirable to limit the number of records visible or to allow sorting.
Mathematical Functions
How to impliment some Mathematical javascript functions within a Service Item.
Multiple Checkbox Option Events
A Customer has a requirement to use Multiple Checkbox Values to Insert and Remove another Question.
Remove Spaces
On occasion the data which is either retrieved into a Service Item or entered into a service item contains leading or trailing white space or may even have more than one space between words.  This can cause problems with any logic that may use the values.  This is an example of javascript which can clean the extra spaces.
Reorder the Elements of a Service Item
Sometimes the elements of a service item (the items in the Pages tab of the Service Item in the Service Catalog Console) can end up "out of order" because one or more element has the same id (sort order) as another element. This will prevent you from moving elements on the page properly, etc. Fixing these duplicate element numbers has always before been a manual process of updating the KS_SRV_ContentsElementHTML form's sortOrder value for the duplicate and all subsequent elements, which can be very time intensive. This service item and handler automates that process of fixing the elements' sort orders.
Retrieve an Answer
Say you have a question on the page named 'First Name', and you need to retrieve the answer of this question to use within a custom javascript event.
Trim leading zeros
This javascript will remove leading zeros from a question and return the value with the zeros removed.
Using a Bridge Search to Populate Questions using a Mobile Friendly Table
This solution describes how to use bridging to do a people search, populating fields on the service item using a bridge request based on criteria the user provides. If there is more than one response to the search, a table is displayed for the user to select the correct individual from. This table uses a mobile friendly version of datatables called FooTables. People Search using Bridges
Using a Bridge Search to Populate Questions using a YUI Table
This solution describes how to use bridging to do a people search, populating fields on the service item using a bridge request based on criteria the user provides. If there is more than one response to the search, a table is displayed for the user to select the correct individual from. This table uses a version of YUI tables. People Search using Bridges
Changing a Check Box Answer from a List to a Column
How to change a CSV list to a vertical stack or column.
Kinetic Request Checkbox To XML
This handler converts a Kinetic Request checkbox answer string into an XML string.
Other