Attached is demo Servoy solution and a screenshot.
I don’t quite understand why they want to return a list of of portal numbers. The only useful thing I could come up with is showing the records being viewed as user feedback. So that is what I did.
The good news: you can indeed get the viewable rows in a portal (but not a tab panel) with the elements.portal.getScrollY() function. All other variables that you need can be calculated from the Y size and row height of the portal. As far as abstraction goes you can get the Y size in a method but you have to know the row height ahead of time.
The bad news is when to fire the code. I have it attached to the label button and to the add and delete portal buttons. But there is no Servoy event detecting scrolling. If you’re thinking “Why not put the code in a calculation” think again – you cannot reference form objects in calculations. Well you can but that is a good way to blow your monitor up and in this case it doesn’t quite work all the way. It got my monitor flickering quite dramatically though.
In regards to whoever did http://www.briandunning.com/cf/684 – my only comment is that those guys need to be coding in Servoy. Because if you can put something like THAT together then Servoy is easy beans.
HOWTO
By the way, if you want a lesson in recursive method techiques, you should download the solution and step through the code.
I use one main called method and two global “function” methods.
1- LABEL_portal_index_location (Main method)
/*****
Returns a list of visible row numbers of a portal
Sample output: "Records 7 to 16 visible"
*****/
//initialize row height variable. portal default is 16
var rowHeight = 16
//get scroll position
var scrollYPos = elements.portal_1.getScrollY()
//call global fx to check if scrollYPos divisible by rowHeight
if (!globals.FX_divisible_check(scrollYPos, rowHeight)) {
//if not, call recursive fx to return nearest number to scrollYPos that is divisible by rowHeight
scrollYPos = globals.FX_divisible_nearest(scrollYPos, rowHeight)
}
//get visible records. 16 is the default portal row height, 20 is for the header
//NOTE: this means your portal must have a Y size that is divisible by 16 plus 4!
//in this demo the portal Y size is 16 * 16 + 4 = 260
var recVisible = (elements.portal_1.getHeight() - 20) / rowHeight
//get visible start and end record numbers
var recStart = (scrollYPos / rowHeight) + 1
var recEnd = (example_data_to_example_data_items.getSize() > (recVisible + recStart - 1)) ? recVisible + recStart - 1 : example_data_to_example_data_items.getSize()
//write results to a label
elements.lbl_portal.text = "Records " + recStart + " to " + recEnd + " visible"
2- FX_divisible_check (Global boolean check)
/****
Purpose check if number is divisible
Input 1 number to act on
Input 2 divisor
Returns true or false
****/
return (arguments[0]%arguments[1] == 0) ? true : false
3- FX_divisible_nearest (Global recursive)
/****
Purpose recursive fx to find the nearest divisible value
Input 1 number to act on
Input 2 divisor
Returns nearest divisible value to input 1
Note to track values in recursive methods you need to use a global variable
even method defined global variables won't work as they will scope to
current running method
****/
globals.fx_nearest_divisible = arguments[0]
var divisor = arguments[1]
//if not divisible keep calling self until divisible
if (!globals.FX_divisible_check(globals.fx_nearest_divisible, divisor)) {
var remaining = globals.fx_nearest_divisible%divisor
if (remaining < divisor/2) {
globals.FX_divisible_nearest(globals.fx_nearest_divisible - remaining, divisor)
}
else {
globals.FX_divisible_nearest(globals.fx_nearest_divisible + remaining/2, divisor)
}
}
return globals.fx_nearest_divisible
portal.servoy (7.4 KB)