Session does not save - asp.net

I'm very new to ASP.NET so there is a high risk that I am missing something simple here, but I have a problem with my Session. When I click the "NewTurn" button the first time, it creates the player just as it should, however, when I click it again, somehow all the stats are back as if it got created again (stats such as "health" is back to max value) but I can see in debug mode that it only enters the "if == null" function ONCE.
I don't understand what I am doing wrong, here is the code:
protected void NewTurn_Click(object sender, ImageClickEventArgs e)
{
StartButton.Visible = false;
RulesLink.Visible = false;
NewTurnButton.Visible = true;
if (Session["PrevObject"] == null)
{
Character player = new Character(1);
Session["PrevObject"] = player;
}
Character prevObj = (Character)Session["PrevObject"];
prevObj = CreateCard(prevObj);
Session["PrevObject"] = prevObj;
}
EDIT: I found the error and it had nothing to do with the Session, I just returned the object without setting the correct values before sending it back. Thank you for your suggestions, though and I'm sorry to have wasted your time!

please check comment in your code
protected void NewTurn_Click(object sender, ImageClickEventArgs e)
{
StartButton.Visible = false;
RulesLink.Visible = false;
NewTurnButton.Visible = true;
if (Session["PrevObject"] == null)
{
Character player = new Character(1);
Session["PrevObject"] = player;
}
Character prevObj = (Character)Session["PrevObject"];
// I think here you made mistake
prevObj = CreateCard(prevObj);
// check here again using DEbug point
// and make sure prevObj not null
Session["PrevObject"] = prevObj;
}

You should have to mention the Property of the player will be assign to the Session["PrevObject"].
suppose I have the class such as
public class Character
{
public playtime{get;set;}
Character(int i)
{
playtime=i;
}
}
Now I will code as you mention:
protected void NewTurn_Click(object sender, ImageClickEventArgs e)
{
StartButton.Visible = false;
RulesLink.Visible = false;
NewTurnButton.Visible = true;
if (Session["PrevObject"] == null)
{
Character player = new Character(1);
//Here is a little change you will have to specify what shuold be assign to the Session //variable
Session["PrevObject"] = player.playtime;
}
Hope this will help you.
Vote if you find helpful
Thanks is always appreciated.

Related

ASP.NET| checkbox's "checked=true" is not setted in the right checkbox

I'm working on a simple multi-staged registration page for a site I'm building, and I give the user the choice of choosing programs/programming languages he knows using checkboxes:
but when I hit the "next" button, in order to go to the next stage, the checkbox I checked isn't set to true, but checkbox no. 18 is set to true(although I didn't check it)
I'm certain it has something to do with the stage before this one, in which I'm building dynamically radio buttons in which the user is choosing his profession (such as Artist, singer and etc').
there are 17 radio buttons, and they are somehow interfering with the next stage, in which the checkbox's checked values are only starting from checkbox no. 18 as I mentioned earlier.
here is some of the code:
else if (int.Parse(ViewState["DivID"].ToString()) == 2)
{
// save the Birthday Date, Language and country of the user.
ViewState["year"] = int.Parse(DropDownYear.SelectedValue);
ViewState["month"] = int.Parse(DropDownMonth.SelectedValue);
ViewState["day"] = int.Parse(DropDownDay.SelectedValue);
ViewState["Language"] = int.Parse(langDropDown.SelectedValue);
ViewState["Country"] = int.Parse(CountryDropDown.SelectedValue);
// ---------------------------------------------
// change from part 2 of the registration to part 3
registrationP2.Visible = false;
BindProfessions(radios, Page);
registrationP3.Visible = true;
radios.Visible = true;
}
else if (int.Parse(ViewState["DivID"].ToString()) == 3)
{
// change from part 3 of the registration to part 4
ViewState["Profid"] = CheckRadio(radios);
registrationP3.Visible = false;
BindKnowledge(CheckboxCon, Page);
registrationP4.Visible = true;
CheckboxCon.Visible = true;
// ---------------------------------------------
//next.Visible = true;
}
else if(int.Parse(ViewState["DivID"].ToString()) == 4)
{
List<int> v = GetCheckBox(CheckboxCon);
ViewState["Knowids"] = GetCheckBox(CheckboxCon);
}
Binding methods:
public static void BindProfessions(HtmlControl ctrl, Page thispage)
{
List<Profession> Plist = Profession.GetProfessionList();
foreach (Profession p in Plist)
{
HtmlInputRadioButton rd_button = new HtmlInputRadioButton();
const string GROUP_NAME = "Professions";
rd_button.Name = GROUP_NAME;
string LinkID = "P" + p.ProfessionID.ToString();
rd_button.Attributes["id"] = LinkID;
RegisterUserControl userprofession = (RegisterUserControl)thispage.LoadControl("~/RegisterUserControl.ascx");
userprofession.imgP = p.ProfPath;
userprofession.fieldName = p.ProfName;
userprofession.IDnum = p.ProfessionID;
userprofession.RadioName = LinkID;
userprofession.EnableViewState = false;
rd_button.EnableViewState = false;
ctrl.Controls.Add(rd_button);
rd_button.Value = p.ProfessionID.ToString();
ctrl.Controls.Add(userprofession);
}
}
public static void BindKnowledge(HtmlControl ctrl, Page thispage)
{
List<Knowledge> Plist = Knowledge.RetKnowledgeList();
foreach (Knowledge p in Plist)
{
HtmlInputCheckBox rd_button = new HtmlInputCheckBox();
const string GROUP_NAME = "knowledge";
rd_button.Name = GROUP_NAME;
string LinkID = "Know" + p.ProgramID.ToString();
rd_button.Attributes["id"] = LinkID;
rd_button.Value = p.ProgramID.ToString();
RegisterUserControl userprofession = (RegisterUserControl)thispage.LoadControl("~/RegisterUserControl.ascx");
userprofession.imgP = p.ProgPath;
userprofession.fieldName = p.PName;
userprofession.IDnum = p.ProgramID;
userprofession.RadioName = LinkID;
userprofession.EnableViewState = false;
rd_button.EnableViewState = false;
ctrl.Controls.Add(rd_button);
ctrl.Controls.Add(userprofession);
}
}
checking methods for both radios and checkbox :
public static int CheckRadio(HtmlControl ctrl)
{
try
{
int counter = 0;
int id = -1;
foreach (Control rdButton in ctrl.Controls)
{
if (rdButton is HtmlInputRadioButton)
{
HtmlInputRadioButton bu = (HtmlInputRadioButton)rdButton;
if (bu.Checked)
{
counter++;
id = int.Parse(bu.Value);
}
}
}
if (counter > 1)
{
return -1;
}
return id;
}
catch (Exception e)
{
return -1;
}
}
public static List<int> GetCheckBox(HtmlControl ctrl)
{
List<int> id_list = new List<int>();
foreach (Control rdButton in ctrl.Controls)
{
if (rdButton is HtmlInputCheckBox)
{
HtmlInputCheckBox bu = (HtmlInputCheckBox)rdButton;
if (bu.Checked)
{
id_list.Add(int.Parse(bu.Value));
}
}
}
return id_list;
}
}
when debugging you can see, that if I choose the first 3 professions, the values returned to me in the List<int> v are 18, 19, and 20
photo: debugging photo
I should mention that after I create the dynamic usercontrols and checkbox/radion buttons, I'm creating them again at postback in protected void Page_Load.
I'm stuck on this for days, and I don't know from where the problem emanates, is it because of ViewState, or the way I'm creating the controls... I really don't know.
Thanks in advance, Idan.
edit:
I played with it a bit, and have found out that when I disable the Binding of the professions which I have initiated earlier in Page_load it does work correctly, page load code look at the second if statement :
protected void Page_Load(object sender, EventArgs e)
{
IsPageRefresh = false;
if (!IsPostBack)
{
ViewState["DivID"] = 1;
ViewState["postids"] = System.Guid.NewGuid().ToString();
Session["postid"] = ViewState["postids"].ToString();
}
else
{
if (ViewState["postids"].ToString() != Session["postid"].ToString())
{
IsPageRefresh = true;
}
Session["postid"] = System.Guid.NewGuid().ToString();
ViewState["postids"] = Session["postid"].ToString();
}
if (int.Parse(ViewState["DivID"].ToString()) == 3)
{
//BindProfessions(radios, Page);
}
else if(int.Parse(ViewState["DivID"].ToString()) == 4)
{
BindKnowledge(CheckboxCon, Page);
}
}
the problem is that I still need to initiate it again after hitting the button in order to get the checked value, how can I fix this thing, and why this is happening? your help would very much be appreciated.
The problem happens because the page recognize that I added 17 new checkbox's, and than when I go over them the first 17 are not checked until the 18'th(the first one of the ones that I checked) what ends up not checking the right checkbox....
And to make it clears I add the other radio buttons to a different div on the page, I don't know what is happening here
for anyone who has the same problem.
I ended up creating the object in Page_PreInit() and it solved the problem, it is recommended(by things I read) to create dynamic objects in Page_PreInit, before anything else is happening to the page.
protected void Page_PreInit(object sender, EventArgs e)
{
try
{
if (!IsPostBack && Session["DivID"] == null)
{
Session["DivID"] = 1;
}
if ((int)Session["DivID"] == 3)
{
InitBindProfessions(Page);
}
else if ((int)Session["DivID"] == 4)
{
InitBindKnowledge(Page);
}
}
catch
{
Response.Redirect("HomePage.aspx");
}
}
InitBindKnowledge and InitBindProfessions are just like BindKnowledge and BindProfession but without adding usercontrols to the control tree

ASP.Net and Parallel.Foreach causes buttons to stop working?

i have a very large database of images from the web which i am categorizing (downloaded locally).
so i have a website (locally) to do this, but the db queries were taking long, so i got an idea to "preload" the next page, so that only the very first load of the page would be slow. I save the list of items loaded in a seperate thread in session. So far so good.
I wanted to optimize further, and did some testing on what took the longest, and loading the images to check the size to see if i needed to scale them (set image height and width on the img obj) - so i wanted to do this with a parallel.foreach loop - but after doing this, my buttons on the page stopped responding? i can see the page runs through the page_load event when i press a button, but it doesn't reach the buttons "code":
protected virtual void btnSaveFollowPosts_Click(object sender, EventArgs e)
{...}
any take on what i am doing wrong? i have tried to limit the degree of paralellelism to 1 just to see if that would fix it - but it did not.
Update - code:
trying to boil it down:
protected void Page_Load(object sender, EventArgs e)
{
Search(false);
}
protected void Search(bool updateCounters)
{
if (Session[SessionItems] == null)
{
if (Session[SessionItemsCache] == null)
{
//if is being constructed, wait, else construct
//if construction is not running
if (Session[SessionCacheConstructionRunning] == null)
{
StartPreLoadContent();
}
while (Session[SessionCacheConstructionRunning] != null)
{
Thread.Sleep(25); //block main thread untill items ready
}
}
List<ContentView> contentViewList = Session[SessionItemsCache] as List<ContentView>;
Session[SessionItemsCache] = null; //clean preload cache
Session[SessionItems] = contentViewList; //save in current usage storage
Filltable(ref tblContent, contentViewList);
//preload next batch
StartPreLoadContent();
}
else
{
List<ContentView> contentViewList = Session[SessionItems] as List<ContentView>; //get items from session
Session[SessionItems] = contentViewList; //save in current usage storage
Filltable(ref tblContent, contentViewList);
}
}
protected void StartPreLoadContent()
{
Session[SessionCacheConstructionRunning] = true;
//start task
Thread obj = new Thread(new ThreadStart(RunPreLoadContent));
obj.IsBackground = true;
obj.Start();
}
protected void RunPreLoadContent()
{
using (DBEntities entities = new DBEntities())
{
entities.CommandTimeout = 86400;
IQueryable<ContentView> query = entities.ContentView.Where(some criterias);
List<ContentView> contentViewListCache = query.ToList();
ParallelOptions options = new ParallelOptions();
options.MaxDegreeOfParallelism = 7;
Parallel.ForEach(contentViewListCache, options, content =>
{
try
{
Interlocked.Increment(ref imageSizeCount);
string path = Path.Combine(basePath, content.LocalPath);
int imageSize = 150;
using (System.Drawing.Image realImage = System.Drawing.Image.FromFile(path))
{
double scale = 0;
if (realImage.Height > realImage.Width)
{
scale = (double)realImage.Height / imageSize;
}
else
{
scale = (double)realImage.Width / imageSize;
}
if (scale > 1)
{
content.ImageHeight = (int)((double)realImage.Height / scale);
content.ImageWidth = (int)((double)realImage.Width / scale);
content.ImageScaled = true;
}
content.ShowImage = true;
}
}
catch (Exception)
{
}
});
Session[SessionItemsCache] = contentViewListCache;
Session[SessionCacheConstructionRunning] = null; //cache ready
}
protected virtual void btnSave_Click(object sender, EventArgs e)
{
try
{
//save
...some reading and saving going on here...
//update
Session[SessionItems] = null;
Search(true);
}
catch (Exception error)
{
ShowError(error);
}
}
I agree with a previous comment: you should probably do this logic earlier in the page lifecycle. Consider overriding OnInit and putting it there.
Also, you could try this line of code instead of your current thread code (which is more suited to Windows not Web programming):
using System.Threading.Tasks;
Task.Run(() => { RunPreLoadContent(); });

How to show the NavigationMenu after you hide it in ASP.NET?

I need to make some of the NavigationMenu items visible only to some users.
In my case I need to make 2 of them available only to admin.
I searched google and I found a command which works :
NavigationMenu.Items.Remove(NavigationMenu.FindItem("HERE GOES THE NAME OF THE MENU I NEED TO REMOVE"));
Till here,everything is ok.
But which command do I need to use to make it available again ?
Please help me. Thnx in advance ;)
public partial class SiteMaster : System.Web.UI.MasterPage
{
protected void Page_Load(object sender, EventArgs e)
{
NavigationMenu.Items.Remove(NavigationMenu.FindItem("Employers"));
if (Matrix.UserLoggedId == Guid.Empty)
{
hlLogin.Visible = true;
lblUsername.Visible = false;
lnkLogout.Visible = false;
}
else
{
// here goes the code to add the menu
hlLogin.Visible = false;
lblUsername.Visible = true;
lnkLogout.Visible = true;
Marin.Employee.DetailsDataTable emp = Matrix.GetEmployeeByUniqueId(Matrix.UserLoggedId);
if (emp.Rows.Count > 0)
{
lblUsername.Text = emp.Rows[0]["Firstname"].ToString();
bool isAdmin =Convert.ToBoolean(emp.Rows[0]["isAdmin"]);
if (isAdmin)
{
//here goes the code to show the menu
}
else
{
NavigationMenu.Items.Remove(NavigationMenu.FindItem("Employers"));
}
}
}
}
Try this, replace x with correct values.
var mi = new MenuItem(x,x,x,x)
NavigationMenu.Items.Add(mi);
For more info on MenuItem check this -
http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.menuitem.aspx

ProfileCommon could be not found

I got error ProfileCommon could be not found , in my code. I don't know how to fix the error. I put namespace using system.Web.Profile, but error still does here. Could someone help how to do that? Please help me if you know. Thank you
public partial class UserProfile : System.Web.UI.UserControl
{
private string _userName = "";
public string UserName
{
get { return _userName; }
set { _userName = value; }
}
protected void Page_Init(object sender, EventArgs e)
{
this.Page.RegisterRequiresControlState(this);
}
protected override void LoadControlState(object savedState)
{
object[] ctlState = (object[])savedState;
base.LoadControlState(ctlState[0]);
_userName = (string)ctlState[1];
}
protected override object SaveControlState()
{
object[] ctlState = new object[2];
ctlState[0] = base.SaveControlState();
ctlState[1] = _userName;
return ctlState;
}
protected void Page_Load(object sender, EventArgs e)
{
if (!this.IsPostBack)
{
// if the UserName property contains an emtpy string, retrieve the profile
// for the current user, otherwise for the specified user
ProfileCommon profile = this.Profile;
if (this.UserName.Length > 0)
profile = this.Profile.GetProfile(this.UserName);
txtFirstName.Text = profile.FirstName;
txtLastName.Text = profile.LastName;
ddlGenders.SelectedValue = profile.Gender;
if (profile.BirthDate != DateTime.MinValue)
txtBirthDate.Text = profile.BirthDate.ToShortDateString();
ddlOccupations.SelectedValue = profile.Occupation;
txtWebsite.Text = profile.Website;
txtStreet.Text = profile.Address.Street;
txtCity.Text = profile.Address.City;
txtPostalCode.Text = profile.Address.PostalCode;
txtState.Text = profile.Address.State;
txtPhone.Text = profile.Contacts.Phone;
txtFax.Text = profile.Contacts.Fax;
}
}
public void Save()
{
// if the UserName property contains an emtpy string, save the current user's
// profile, othwerwise save the profile for the specified user
ProfileCommon profile = this.Profile;
if (this.UserName.Length > 0)
profile = this.Profile.GetProfile(this.UserName);
profile.FirstName = txtFirstName.Text;
profile.LastName = txtLastName.Text;
profile.Gender = ddlGenders.SelectedValue;
if (txtBirthDate.Text.Trim().Length > 0)
profile.BirthDate = DateTime.Parse(txtBirthDate.Text);
profile.Occupation = ddlOccupations.SelectedValue;
profile.Website = txtWebsite.Text;
profile.Address.Street = txtStreet.Text;
profile.Address.City = txtCity.Text;
profile.Address.PostalCode = txtPostalCode.Text;
profile.Address.State = txtState.Text;
profile.Contacts.Phone = txtPhone.Text;
profile.Contacts.Fax = txtFax.Text;
profile.Save();
}
}
As Mark pointed out, profiles only work out-of-the-box with the website template and I have blogged instructions on how to use the plug-in to facilitate the use of profiles for the Web Application project:
http://www.codersbarn.com/post/2008/07/10/ASPNET-PayPal-Subscriptions-IPN.aspx
It is possible to do it yourself, and here's a fully working implementation that you can download:
http://leedumond.com/blog/asp-net-profiles-in-web-application-projects/
According to these links(link1, link2)
Web Applications don't support the auto generation of the ProfileCommon object
The first link then give's a link to a VS Addin and instructions on how to incorporate it into the build process in order to work around the problem
There is a very simple work-around for this, for all coders who just want to hack on with things. You can get the ProfileBase type and load the profile into that, but you lose strong typing. If you are in control of the data in the profile, or you are sure that the data in the profile is of a certain type, you are good to go.
string user = "Steve"; // The username you are trying to get the profile for.
bool isAuthenticated = false;
MembershipUser mu = Membership.GetUser(user);
if (mu != null)
{
// User exists - Try to load profile
ProfileBase pb = ProfileBase.Create(user, isAuthenticated);
if (pb != null)
{
// Profile loaded - Try to access profile data element.
// ProfileBase stores data as objects in (I assume) a Dictionary
// so you have to cast and check that the cast succeeds.
string myData = (string)pb["MyKey"];
if (!string.IsNullOrWhiteSpace(myData))
{
// Woo-hoo - We're in data city, baby!
Console.WriteLine("Is this your card? " + myData + " - Ta Dah!");
}
}
}

AsyncFileUpload Control

I am using the new AsyncFileUpload control from the latest AjaxControl ToolKit.
My query is regarding the OnClientUploadStarted event which is fired before the upload is started. Is there any way to cancel the upload, as I am checking the fileExtension at this point and would like to cancel the upload so that it does not continue and go on to upload the file. My end result is allow only images to be uploaded.
Please advise and thanks for your time.
Got the answer, all I had to do was override the javascript function with this script(not the best answer, but works), you all could have done faster and cleaner
var orig = AjaxControlToolkit.AsyncFileUpload.prototype.raiseUploadStarted;
AjaxControlToolkit.AsyncFileUpload.prototype.raiseUploadStarted = function(e) {
var evt = this.get_events()._getEvent('uploadStarted');
if (evt) {
if (evt.length > 1)
return orig(e);
else if (evt.length === 1)
return evt[0](this, e);
}
}
You might try adding a "Regular Expression Validator" to the field, and see if you can use that to validate the file selected before the upload starts.
Try this code:
protected void AsyncFileUpload1_UploadedComplete(object sender, AjaxControlToolkit.AsyncFileUploadEventArgs e)
{
if (rdoFileType.SelectedValue == String.Empty)
{
lblStatus.Text = "Please select a file type before selecting a file.";
AsyncFileUpload1.FailedValidation = true;
e.state = AjaxControlToolkit.AsyncFileUploadState.Failed;
return;
}
try
{
// System.Threading.Thread.Sleep(5000);
if (AsyncFileUpload1.HasFile)
{
string _filename = System.IO.Path.GetFileName(e.filename);
System.IO.FileInfo f = new System.IO.FileInfo(AsyncFileUpload1.PostedFile.FileName);
if (rdoFileType.SelectedValue == "F")
{
if (f.Extension != ".pdf")
{
lblStatus.Text = "Final Document must be a .pdf";
e.state = AjaxControlToolkit.AsyncFileUploadState.Failed;
e.statusMessage = "Final Document must be a .pdf";
throw new Exception("Final Document must be a .pdf");
}

Resources