I am sure this is something simple, but can someone show me how we return the selected value from a HTMLDropDown?
In my Process class I have defined the attribute for the selected variable and I have generated the cursor that populates the list;
Function cdep_2()
#If .F.
Local Request As wwrequest, Response As wwpageresponse, Process As wwprocess
#Endif
Local lc_SelDept As Character
Local lc_DeptOut As Character
Store "001" to lc_SelDept
If !Request.IsPostBack()
sele * from myTable into cursor cDept
endif
Response.ExpandTemplate()
endfunc
In my HTML file which is a WC content template page, (for arguments sake called cDep_2.wcx) I have the following;
<%
* VS Addin Comment: SourceFile="~\..\deploy\cdeprocess.PRG"
pcPageTitle = "cdep_2"
%>
<% Layout="/views/_cdep_layoutpage.wcs" %>
<div id="xLeft" style="float:left; width:25%; background-color:cornsilk;">
<%= HtmlDropDown("lstDept",
"lc_SelDept",
"cDept",
"alltrim(code)",
"alltrim(attribute_)",
"",
"--- Select a Department")
%>
</div>
<!-- remove sections if you're not using them -->
<% section="headers" %>
<% endsection %>
<% section="scripts" %>
<% endsection %>
I believe I have populated everything correctly:
- [1] Name of the dropdown list in the rendered code is "lstDept"
- [2] the selected value goes to the variable lc_SelDept
- [3] data to populate the list comes from the cursor cDept
- [4] the attribute in the file to get the 'value' for/from the list is the variable "code"
- [5] the text to populate the dropdown list comes from the field 'attribute_'
- [6] no other html required
- [7] the text first seen in the list is "--- Select a Department"
The dropdown renders perfectly, but, how do I pull the selected values specified when the user selects from the drop down list? I thought it might be in the lc_selDept variable but it appears not to change.
I've tried display it simply as;
The selected value is:
<br/>
<%= lc_SelDept %>
<br/>
but I get a message that this renders an error.
Can someone help in letting me know how to pull the value from the selected list?
thx Serge
First you need to make sure that the drop down is inside of a <form>
tag that submits the form to the server (or an AJAX request which will be different):
<form action="">
<%= HtmlDropDown(...)
<button type="submit">Send</button>
</form>
Use an empty action=""
to post back to the same page you came from, otherwise give it a new URL.
You also need a button to submit the form although you can add an AutoPostback="true"
to the control to force it to submit. You may still need a button (invisible if necessary) to submit the form reliably in all browsers.
Assuming this is a form post to capture the value then:
lcSelVal = Request.Form("lstDept")
+++ Rick ---
Hi Rick,
Everything works as planned - thank you very much! Once I saw how data was being returned from the form to the server it was academic ~ the framework worked flawlessly! I have been working with how data is moved back and forth and I have a question regarding the scope visibility of variables. For example in my example from before I've been able to trap a number of different form elements and capturing their input values as you had outlined.
My question becomes primarily one of SCOPE and secondarily a question regarding using Method="GET" vs. Method="POST" in the HTML form element.
1st question: In the FoxPro code, I added a little updater to the page which tells me of the postback, and the counter. Oddly enough everything here works except the iCnter variable (defined as public). All the HTMLDropDown list variables created and their return values are returned and processed perfectly. The iCnter variable presents properly when the page is first shown (not postback()) but following this on postback it does not increment and throws an error as not being defined.
2nd Question: If I was to use Method="GET" the return data populates in the URL and it appears that I should be able to process it through (Request.QueryString(..whatever..)). Would this be the case? When I do use Method="GET" however, the page actually does not appear to toggle the postback() as one would expect. Can you provide some insight around this.
In my foxpro code I trap the request form using 'lcReadValue=(request.form())' enabling to capture the entire set of attributes and values found in the form element on the HTML page. The nItems block only executes if I read in data from the 'request.form())' stub.
The foxpro code is shown below, followed by the HTML.
Function cdep_2()
#If .F.
Local Request As wwrequest, Response As wwpageresponse, Process As wwprocess
#Endif
PRIVATE iCnter as Integer
Local rPos As Integer, iStartValue As Integer, cWhichMethod as Character, isGoodGet as Boolean
STORE "" TO cWhichMethod
Store 1 To rPos, iStartValue
lc_pk = This.decode(Request.querystring("Shtoh"))
lcReadValue= (Request.Form())
nItems = Occurs("&",lcReadValue)
If !Request.IsPostBack()
Store "Not Postback" To sgaMessageCheck
Store Int(Val(lc_pk)) To iPK
If iPK=0 .Or. Empty(lc_pk)
c_PKID = Session.getsessionvar("sgaPK")
If Empty(c_PKID)
Store 0 To iiPK
Else
iiPK = Int(Val(c_PKID))
Endif
Endif
iPK = Iif(iPK >= 1, iPK, Iif(iiPK >=1, iiPK, 0))
If iPK > 0
ologin=Createobject("sgalogin")
isGoodGet = ologin.Load(iPK)
If isGoodGet
lc_uCrs = Alltrim(ologin.oData.usr_direct)
lc_pk = Transform(ologin.oData.pk)
Session.setsessionvar("sgaPK",lc_pk)
Session.setsessionvar("sgaCrs",lc_uCrs)
txt_cpk = This.encode(Transform(iPK))
Endif
Else
=Response.redirect([sgaLogin.c1?Shtoh=] + This.encode(lc_pk) )
Endif
iCnter = 1
Else
Store "Is a Postback" To sgaMessageCheck
lc_uCrs = Session.getsessionvar("sgaCrs")
lc_pk = Session.getsessionvar("sgaPK")
iCnter=iCnter+1
Endif
If nItems >=1
Dimension aReadItemsArray(nItems), cTrimVar(nItems+1), cActualVar(nItems+1), cActualVal(nItems+1), iStartPos(nItems+1), iEndPos(nItems+1)
For j=1 To nItems
aReadItemsArray(j)=At("&",lcReadValue,j)
Endfor
For j=1 To nItems+1
Do Case
Case j=1
iStartPos(j)=1
iEndPos(j)=aReadItemsArray(j)
Case j <= nItems
iStartPos(j)=aReadItemsArray(j-1)+1
iEndPos(j)=aReadItemsArray(j)
Case j = nItems+1
iStartPos(j)=aReadItemsArray(j-1)+1
iEndPos(j)=Len(lcReadValue)+1
Endcase
Endfor
For j=1 To nItems+1
cTrimVar(j)=Substr(lcReadValue,iStartPos(j),iEndPos(j)-iStartPos(j))
Endfor
For j=1 To nItems+1
rPos = At("=",cTrimVar(j))
cActualVar(j) = Substr(cTrimVar(j),1,rPos-1)
If rPos = Len(cTrimVar(j))
cActualVal(j)=""
Else
cActualVal(j) = Substr(cTrimVar(j),rPos+1,Len(cTrimVar(j)))
Endif
Do Case
Case cActualVar(j)="lstDept"
Store cActualVal(j) To lcSelectedDepartment
Case cActualVar(j)="lstClass"
Store cActualVal(j) To lcSelectedClass
Case cActualVar(j)="lstMFG"
Store cActualVal(j) To lcSelectedMFG
Case cActualVar(j)="lstStores"
Store cActualVal(j) To lcSelectedStores
Case cActualVar(j)="lstProdID"
Store cActualVal(j) To lcSelectedProdID
Case cActualVar(j)="lstProdType"
Store cActualVal(j) To lcSelectedProdType
Endcase
Endfor
Endif
If isGoodGet
Store "Yes" To sga_GetResult
Else
Store "No" To sga_GetResult
Endif
Response.ExpandTemplate()
Endfunc
Here's the HTML. Note that the counter variable iCnter I dropped in works on initialization then throws an error upon any postback() page
<%
* VS Addin Comment: SourceFile="~\..\deploy\cdeprocess.PRG"
pcPageTitle = "cdep_2"
%>
<% Layout="/views/_cdep_layoutpage.wcs" %>
<% if sga_GetResult="Yes" %>
<input type="hidden" name="cpk" value="<%= txt_cpk %>" />
<% endif %>
<% if sga_GetResult="No" %>
<input type="hidden" name="cpk" value="0" />
<% endif %>
... a bunch of HTML stuff ...
<form action="" method="POST">
<div style="float:left; margin-left:10px; margin-bottom:10px;">
<div id="xLeft" style="float:left; margin-left:10px; margin-bottom:2px;">
<div id="xLeft2" style="float:left; width:110px;">
<i class="fas fa-building" style="color:green"></i>
Department:
</div>
<div id="xLeft3" style="float:left;">
<%= HtmlDropDown( "lstDept","lc_SelDept","cDept","alltrim(code)","alltrim(attribute_)","","--- Select a Department","" ) %>
</div>
<br />
</div>
<div id="xRight" style="float:left; margin-left:10px; margin-bottom:2px;">
<div id="xLeft4" style="float:left; width:110px;">
<i class="fas fa-chess-king" style="color:maroon"></i>
Class:
</div>
<div id="xLeft5" style="float:left;">
<%= HtmlDropDown("lstClass","lc_SelClass","cClass","alltrim(code)","alltrim(attribute_)","","--- Select a Class","" ) %>
</div>
<br />
</div>
<div id="yLeft" style="float:left; margin-left:10px; margin-bottom:2px;">
<div id="xLeft6" style="float:left; width:110px;">
<i class="fas fa-industry" style="color:darkblue"></i>
Manufacturer:
</div>
<div id="xLeft7" style="float:left;">
<%= HtmlDropDown("lstMFG","lc_SelMFG","cMFG","alltrim(code)","alltrim(attribute_)","","--- Select a Manufacturer","" ) %>
</div>
<br />
</div>
<div id="yRight" style="float:left; margin-left:10px; margin-bottom:2px;">
<div id="xLeft8" style="float:left; width:110px;">
<i class="fas fa-shopping-cart" style="color:indigo"></i>
Store:
</div>
<div id="xLeft9" style="float:left;">
<%= HtmlDropDown("lstStores","lc_SelStore","cStore","alltrim(code)","alltrim(attribute_)","","--- Select a Store","" ) %>
</div>
<br />
</div>
<div id="zRight" style="float:left; margin-left:10px; margin-bottom:20px;">
<div id="xLeft11" style="float:left; width:110px;">
<i class="fas fa-scroll" style="color:darkmagenta"></i>
Product Type:
</div>
<div id="xLeft12" style="float:left;">
<%= HtmlDropDown("lstProdType","lc_SelPType","cProdCode","alltrim(code)","alltrim(attribute_)","","--- Select Product Type","" ) %>
</div>
<br />
</div>
</div>
<div style="float:left; margin-left:20px; margin-top:10px; width:100px;">
<button type ="submit" style="width:150px;">Add Parameter</button>
</div>
</form>
... more closing HTML stuff ...
<!-- Dumping the data to be used later in processing -->
sgaMessageCheck: <%= sgaMessageCheck %> <br />
iCnter: <%= iCnter %> <br /><br /><br />
lcSelectedDepartment: <%= lcSelectedDepartment %> <br />
lcSelectedClass: <%= lcSelectedClass %> <br />
lcSelectedMFG: <%= lcSelectedMFG %> <br />
lcSelectedStore: <%= lcSelectedStores %> <br />
lcReadValue: <%= lcReadValue %> <br />
</div>
<!-- remove sections if you're not using them -->
<% section="headers" %>
<% endsection %>
<% section="scripts" %>
<% endsection %>
So everything I need to work with presents properly which is most important. However should I need to increment a counter why does iCnter fail. Also can you explain the action around what happens with Method="GET" as opposed to Method="POST" as I had noted...
Naturally I could recall this page with action="cDep_2.c1?" in the form tag I suppose, however, I like the way data was moved from the form to the server the way you had suggested earlier.
Thanks for any help you could provide! Serge
Please try to post more focused questions and don't combine questions that are already ontop of long thread. It's better to start new questions that are focused on the problem at hand.
2nd Question: If I was to use Method="GET" the return data populates in the URL and it appears that I should be able to process it through (Request.QueryString(..whatever..)). Would this be the case? When I do use Method="GET" however, the page actually does not appear to toggle the postback() as one would expect. Can you provide some insight around this.
As the name suggests IsPostBack()
checks whether the form is POST
ing back, so no if you GET it's not going to work. Nor should you use GET for forms unless the form only sends ID data. GET is not meant for data - it's meant for identification or routing. Data should always go into a POST.
+++ Rick ---