Pageframe [examples]


// VFP custom section for page "page1" section "section1"
namespace rectabs
public pageframe1, tab0, tab1, tab2
define class page1_section1 as section
define class tabbutton as CommandButton 
proc click
	do case
		case upper( = "TABBUTTON1"
			pageframe1.activepage = 1
		case upper( = "TABBUTTON2"
			pageframe1.activepage = 2
		case upper( = "TABBUTTON3"
		case upper( = "TABBUTTON4"
			pageframe1.closable = not pageframe1.closable
		case upper( = "TABBUTTON5"
			pageframe1.tabs = not pageframe1.tabs
		case upper( = "TABBUTTON6"
			if pageframe1.pagecount = 3
				tab2.caption = "Tab2"
				tab2.backcolor = "green"
proc page1_section1 
	page1_section1 = createobject("page1_section1")
	page1_section1.addobject("pageframe1", "pageframe")
	pageframe1.addobject("tab0", "page")
	tab0.layout = 3
	tab0.picture = ":/images/recital_background"
	tab0.caption = "Tab0"
	tab0.addobject("tabbutton1", "tabbutton")
	tabbutton1.caption = "Select Tab1"
	tab0.addobject("tabbutton2", "tabbutton")
	tabbutton2.caption = "Select Tab2"
	tab0.addobject("tabbutton3", "tabbutton")
	tabbutton3.caption = "Display Pagecount"
	tab0.addobject("tabbutton4", "tabbutton")
	tabbutton4.caption = "Toggle closable tabs"
	tab0.addobject("tabbutton5", "tabbutton")
	tabbutton5.caption = "Toggle tab bar"
	tab0.addobject("tabbutton6", "tabbutton")
	tabbutton6.caption = "Add/remove tab"
	pageframe1.addobject("tab1", "page")
	tab1.caption = "Tab1"
	tab1.backcolor = "red"
	pageframe1.addobject("tab2", "page")
	tab2.caption = "Tab2"
	tab2.backcolor = "blue"
return page1_section1


Page [examples]

Create a page in the current App


// Create a page in the current App 

create page mypage

To get a reference to a page with the id mypage.

Oitem = Lianja.getElementByID("mypage")

// to set the value of an Attribute

// to get the value of an Attribute

cTitle = Lianja.get("pageid").getAttribute("title")

Note: on the desktop, the shortened form getAttr(name) is also available.

Switching between pages

To switch pages just do this:


This will cause the page named mypagename to be made visible in the viewport.

The left sidebar can also be hidden/shown using the showdocument() function or the Lianja.showDocument() method:


The right sidebar can also be hidden/shown using the showdocument() function or the Lianja.showDocument() method:


Note: in the Web/Mobile client the Page must start with a visible right sidebar (Show right sidebar attribute) to use the hiderightsidebar/showrightsidebar actions.

The URL of the content to be displayed.

In the example shown above a Google Chart is displayed (line breaks have been added to the URL here):
&chd=t:{rsidebar2(  "{{customers.customerid}}" )}
&chco=fac400|FFFF42|4685e2&chtt=Orders per year&chbh=33

Note also the use of the rsidebar2 Lianja/VFP function (rsidebar2.prg).

The URL of the content to be displayed.

In the example shown above a Google Chart is displayed (line breaks have been added to the URL here):
&chd=t:{rsidebar3( "{{customers.customerid}}" )}
&chco=fac400|ffff42|4685e2&chtt=Order amount (US$)&chds=0,16000

Note also the use of the rsidebar3 Lianja/VFP function (rsidebar3.prg).



I have looked at the Page Center video and the example_PageCenter.

I am trying this in a web app.
When I Preview, how do I get it to start on the PageCenter page?

I tried this:
Under Settings, the Initial page is set to the pageCenter page. But it does not respect this. It always opens a page. (Clicking the Hamburger menu does go to the PageCenter page).

I compared my Settings to the Example settings. Didn’t spot anything obvious.

BTW I did a visual comparison. Is there a way to compare the settings of 2 projects automatically?
If it doesn’t already exist, it would be handy to be able to get a report of Settings and Attributes that are different from the defaults. This would help with learning from the sample apps.

When on the PageCenter page itself, is there a way to turn off the display of the Hamburger menu (because it doesn’t do anything):

Name:  2017-05-11_17-05-07.jpg Views: 40 Size:  27.8 KB


Move the Page Center page in the Pages menu so that it is the first page loaded, then save and reload the App and the Page Center page will be selected:

Name:  pagecenter.jpg Views: 37 Size:  71.7 KB

The Page attribute ‘Hide hamburger menu’ is currently supported on the Desktop client only.


To hide the hamburger menu when you are using a page center page.

Name:  Screen Shot 2017-05-12 at 10.00.43 AM.jpg Views: 33 Size:  118.5 KB


For an APP with more than 1 pages, how can i set which page as the default first page?I look thru the attributes of APP settings to no avail.


Settings -> General App Configuration -> Initial page


In the Navigation page drag the page you would like to be the default to the top of the pages list.


How can use a command button on click to set the attributes of objects in another page.
Name:  ljpage3.png Views: 26 Size:  11.2 KB

E.g. In page1, I want to set URL of page3:section1, and the label of page3:section2 to “abc”
So in page1 command button click, i put the following code

Lianja.get("page3.section1").url = "newform.html"
Lianja.get("page3.section2.lblText").caption = "abc"


However, the label and the webview remains unchanged.


Lianja.get("page3.section1").url = "newform.html";
// Refer to Canvas formitems by their unique name in lower case
lbltext.caption = "abc";



can you link to the Docs where lbltext.caption = “abc”; should be used as a direct reference please.

Been watching for quite a while and that caught me out somewhat…


Understanding the Lianja HTML5 Client: Building Canvas Sections for Web and Mobile


Page lifecycle? Specifically, I’m looking to understand whether all Pages are created when the app is started and destroyed upon app completion (close) or whether it’s possible to create a Page and have it destroyed at the end of it’s use. In our VFP apps, we often create modal forms and destroy them after collecting the necessary input or displaying the desired output.


Lianja Mobile Apps are Single Page Applications (SPA). A single DOM is sent that contains no data, only the pages. That is the nature of SPA apps, and is the nature of Cordova/PhoneGap apps. Google Docs, etc. work the same way.

What is your concern? Remember that in the modern app age (of SPA apps), there is no monolithic huge app that hogs a ton of memory.


Lianja gives you the ability to define a form and release it when done;I do this in the custom vfp sections.

So within a single page, I can have many forms defined and show them when needed, then release them when done.


Look at Lianja.showDialog() and Lianja.showDialogPanel(). They provide the required functionality.


I have a page that has a Grid section. After double-clicking a row in the grid, I open a page that contains a canvas with fields from the record selected from the table shown on the grid from the prior page. The Actionbar shows that is on record #1. Should this show the record number that was selected from the prior page instead? Or do I need to refresh the Actionbar somehow?


You will need to position the “cursor” on the canvas page. Lianja.showDocument can be used to both switch to the page and set a filter (if it’s a table) or requery (if a view).


treat them as separate, even though you will see one alias(). The alias is used to fill the control. So if you are using a parameterized view and don’t change the WHERE clause, those are the available records.

This is quite different from VFP, where moving the record pointer refreshes all attached controls (although the controls still have to be refreshed to show the change).

As always in Lianja, “think mobile” even if you are using a desktop. In mobile, the data is queried on the backend and then sent in an oData package to the UI. What’s there is there, although it can be filtered.


You can issue a refresh on the target page in its activate delegate. See also the page attribute “Refresh when activated”


Suppose in the event delegate for the click event of a command button I would like to open a page to collect some parameters and when the data entry for that page is complete, perform some sort of processing on the database based on the input from the page. How would I go about doing this? Is it possible to use Showdocument() modally to open the new page, and have control returned to the delegate after the page is closed? (Desktop only – I understand this probably doesn’t make sense in a web/mobile environment.)


Have a look at showdialog and showdialogpanel. You can use these command to either pop-up or slide in another page to handle multiple documents.

You can also define a form as an object, and show it to handle inputs.


I have a page with a single canvas section. When the page is initially displayed, no control has the “focus”. After pressing tab one time, the focus moves to the control I have specified with Tab Order = 1. Successive tabs move through the controls in the correct order. When the last control is reached, tabbing cause the “focus” to move to what I’m guessing is some invisible control as none of my canvas section controls has the focus.

1. Is it possible to have the page start with focus on the first control?

2. Is it possible to prohibit the invisible control from being cycled through when tabbing?

3. How can I find this invisible control?

By the way, the Actionbar is off for the page.


watch the events firing in the app inspector events tab.
you can set the focus to the first field in the page activate delegate.


can I hide the “X” to prevent the accidentally closed of the app?


When using a form window you just need to set the closable property to false.


How do I change:
the order of the tiles on the Page Center page?


I have added “Tile order” under the “Page Center Tile” attributes in the page attributes in the 3.5 release.


I navigate to a different page using Lianja.activePage = page2 & the new page opens just fine. I want to do some things when the page loads (move to a desired record or start add mode etc.). A few questions:
– I did some tests and page load/init/ready all fire when the app starts and never again, am I right in assuming that all pages load up at the start of the app?
– What event could I use to setup a page when navigating to it as above?
Events are called in the order (ILRA)
and then
activate for the active Page/Section.

When you navigate to a Page, its activate event is called.

Have a look at SHOWDOCUMENT() / Lianja.showdocument() for UI operations such as selecting a Page and searching within it
Lianja.showDocument() and Lianja.getElementByID() are core to working with the Lianja Object Model. I would suggest you familiarize yourself with the Lianja system object.

If you have a lot of pages it may be better to spilt it up into several apps.
You can
switch between apps using Lianja.openApp()

I have an app with two pages, when I switch to the second page, my data is synced with the first page as it should be.
However, when I
return to the first page using a command button, the table I am using is closed and I have to reopen it manually or add a use field in my activate delegate, but when I do this, it defaults to the first record.
I looked through my code and cannot find
where the table is closing. Is there a delegate that will keep the table open on my first page so when I return to it, it is still on the same record?
canvas sections on both pages
Are you querying a table which is bound to a section? If you are you need to wrap that code in:


Which will maintain the context of the open cursors.
you got me looking at a section where I had an unneeded select command for a database that was already in use. Problem solved.

Is it possible to establish a child parent relationship between sections of two pages?
No. Sections belong to one page.

So If I want to use the same data on a new page, should I save the index field to a memory variable and filter the table on the new page/section to get the same record data or is there a better way to link two sections.
Basically I am choosing an address record from one page and starting an invoice with the same record on a new page by saving the data memory variables.

I have both sections one on the first page and the other on the second page pointing to the same database and table. When I go to the second page, it is not point to the same record in the table. Almost like it needs a parent – child relationship.
If the sections are bound to the same data, navigating between pages will do that automatically. There is no need to save anything in any variables.
Hint: Look at using Lianja.showdocument(“page2.section1?action=search& text=” + yourkeyexpression) in the activate delegate for page2 to keep them in sync.
If you were really doing parent/child with grids, and they were on separated pages, there is a way to do that also.

If you are using views, you would set the WHERE of the child page to the PK value of the parent record, when Activating the page.

If you are using table, you would set the FILTER of the child page in the same way.

If both cases you would use a macro expression, like so:
parentfk = {}

In desktop apps, even in JavaScript, resetting the WHERE in the Activate of the child section is all you need to do to refresh the child.

Lianja.get("pgChild.scChildGrid").where = Lianja.get("pgChild.scChildGrid").where

add the semi-colon for JavaScript.

you want the page, on opening, to show no records. The reason it is not doing so is that you are in the development environment, and when you set the REQUERY property it is saving.
That’s right: you can set properties by executing commands in development mode, and the values get saved. That’s a great thing (think: builders). This
wouldn’t happen in the deployed app.

So: what you can do is set the REQUERY back to 1=0 in the READY of the section, and the app will start with no records.
testing, you can “refresh” the app to make this happen. In scenarios where you want all records to show, you can set it to 1=1 in the READY.

I’ve try to set the page parameter “Query page”, but I do not see change when I load the page.
That setting is used when you have a web app that does not initially load data.
It is telling Lianja not to automatically try and populate the data.

This is really for instances when you create a virtual Table using the where 1 = 0 clause.
To populate the data after the page has loaded, you would set the where (or filter) clause at runtime.

Lianja.get("page.section").where = 'employeeid =1'


I have added a new attribute in the page attributes “Full page edit“. This causes all sections on a page to be edited when the “Edit” tool button is clicked in the navigation bar (at the bottom) or the page is switched into edit mode using

Lianja.showDocument("page: page1?action=edit")

This provides for a better user experience when a page is laid out in multiple sections and you want to edit the complete “DataView” as opposed to just the main form section that has the “Search Key” field defined.

“Full page edit” also applies to Add – clicking the Page’s Add button or from an Add action:

Lianja.showDocument("page: page1?action=add")

how do I delete an object that is created?

myform = createobject("form")


release myform



<pre class="bbcode_code"myform = .f.

If the form is displayed you need to close() it or release() it.

to declare a variable that is visible to all sections within a page
Just put it in your namespace in the page init delegate.

namespace PeopleKiosk 
public MyVar = 0

If you wanted to reference a formitem in the ‘Customer’ Form Section in example_webapp3, you would use the Lianja.get() syntax, e.g.

// Event delegate for 'click' event
function page1_section2_field23_click()
        m_companyname.text = "";
        m_companyregion.text = "";


How do you change pages programaticaly ?


Showdocument(), which can be called as a function or as a method on the Lianja System Object.

If the page on which the user enters the sales order, after entering the account code, I want to display all of its sales quotation ..
I can use a Sidebar, where I show the list the valid offers?
If you want a ‘Sidebar’ (and not the standard left sidebar with logo, menu, favorites etc.), you can use a Lianja.showdialogpanel() to display a UI Page or a Page Navigation Panel set to use a ‘Custom UI page‘.
Either of these would allow you to design a Page with your required Sections and set/get values using Lianja.get(“page.section.field”).property.

You also have the option of using the Page Right Sidebar with a Custom Content Gadget based on an rsp script containing VFP/HTML/JavaScript.

If I set the Page Header to Visible = .F., the headerbar is shown, even if in the Apps Setting Hide Header Bar = .T.

That’s to allow for Page navigation when you have no Page Header and no Left Sidebar with the Page menu.