Using dynamically generated checkboxes in Apex

In one of my projects, I’m building an application in Apex. This application depends entirely on webservices for its data. Which meant that I had to be smart in my design.
The project revolves around a system in which customers can create a survey. The survey is then presented to individuals using an Apex front-end. This means that all information on the front-end is shown dynamically.
One of the question types that is used, is presented using checkboxes. This proved to be quite a challenge in Application Express.
First of all I needed to understand the inner workings of Apex’s array collections. Normally an item in a form is put into a desired array using code like apex_item.hidden(1,value), which puts a value into array 1. So what I did in my project was to put all values in the form into an array and later select them by using a loop:

for i in 1 .. apex_application.g_F01.count
loop
insert into answer_table (question, answer)
values (APEX_APPLICATION.G_F01(i)
,APEX_APPLICATION.G_F02(i)
);
end loop;

But this is not the way to go with checkboxes, because a webbrowser only sends the checkboxes that are actually checked. This means that when you have a question with 5 possible answers and the user checks 2 of them, you get an array with 2 values per question. But because there is only one question, the arrays for question and answer go out of sync.
After browsing through the Oracle forums, I started to think of a solution to my specific problem.
What I eventually ended up with, was a specific array #40, just for questions with a checkbox. This array holds the question_id concatenated with the checkbox value and a letter X inbetween (because both the question_id and checkbox value are numbers, I can use any non-numeric character). This same array is filled with a hardcoded value for all other items, to distinguish them.
A simple textitem would look something like this:

htp.p(apex_item.hidden(1,question_id));
htp.p(apex_item.text(2,question_content));
htp.p(apex_item.hidden(3,question_type));
htp.p(apex_item.hidden(40,'XXTESTVALUEXX'));

And a checkbox item like this:

htp.p(apex_item.hidden(1,question_id));
htp.p(apex_item.hidden(2,null));
htp.p(apex_item.hidden(3,question_type));
htp.p(apex_item.checkbox(40,question_id||'X'||choice_id,p_checked_values => l_select_list,p_checked_values_delimitor => ';'));

Now when I need to pick up these items in my page, I first form a loop like the one in the beginning of this post with an extra IF to check if APEX_APPLICATION.G_F03(i) is not ‘CHECKBOX’.
After that I go through an extra loop which gets all items in apex_application.g_F40.count and where this statement is true APEX_APPLICATION.G_F40(i) <> 'XXTESTVALUEXX'.
With a little help from instr, substr and replace I can then pull out the question_id and selected checkbox value from array #40.

New Whitebook published

Last week my latest Whitebook article was published at the Whitehorses company website.
The article is on the RFID implementation at Centraal Boekhuis. That is the biggest partner in logistics for books in the Netherlands and Benelux region. There I worked on the first big RFID implementation for a retail supply-chain in the Netherlands.

Find the article here.