Pass data from client side to server side - javascript

I'm writing a ASP.NET application.
I have a page, where user will select or deselect some elements. This happens client-side: when user clicks on a div, javascript function is called and some classes are changed, so the div is "grayed out".
There is also a Save button (asp:Button), that will save data.
What is the best way to pass information about selected elements back to server-side?
I have tried to put that info in cookies. Each div has ID, so I would create cookie with that ID and boolean value. This is a bad idea, because:
- when user (de-)selects some elements, and then navigates away from page without saving
- then navigates back, and without selecting anything clicks "Save", cookies have previous values and that gets saved.

What you have tried is good except Cookies. I can understand the problem you are facing.
So I would suggest to use Hidden Field instead of Cookies.
When your div is get selected call the javascript function and store the value (in specific format) in hidden field. and In the same way when your div is deselected remove the value from the HiddenField.
You can store value in HiddenField in below format (ID:value) :
div1:true;div2:true;div3:true
Now on the click event of the button you can first split the values by semicolon (';') and you will get the array like this :
div1:true,
div2:true,
div3:false
for each value again split the value by colon (':') and you will get the div id at the 0th index and its value on first index.
So basically your code to get the values from hidden field and perform an action on it would be as mentioned below :
foreach (var selectedDiv in this.hfSelected.Value.Split(';'))
{
var divId = selectedDiv.Split(':')[0];
var divValue = selectedDiv.Split(':')[1];
// Perform action on divId and divValue
}
Update :
To store the value in HiddenField, instead of div click, you can use the OnClientClick event of the button and get the value of selected and deselected div. See my below code sample :
ASPX Page :
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
<title></title>
<script type="text/javascript" src="Scripts/jquery-1.8.2.js" language="javascript"></script>
<script type="text/javascript" src="Scripts/jquery-1.8.2.min.js" language="javascript"></script>
<script type="text/javascript" src="Scripts/jquery-ui-1.9.1.custom.js" language="javascript"></script>
<script type="text/javascript" src="Scripts/jquery-ui-1.9.1.custom.min.js" language="javascript"></script>
<style type="text/css">
.selectedDiv {
background-color: #333;
color: #fff;
height: 30px;
width: 100%;
}
.deselectedDiv {
background-color: #bababa;
color: #000;
height: 30px;
width: 100%;
}
</style>
</head>
<body>
<form id="form1" runat="server">
<div class="selectedDiv" id="div1">I am Div 1</div>
<div class="selectedDiv" id="div2">I am Div 2</div>
<div class="selectedDiv" id="div3">I am Div 3</div>
<div class="selectedDiv" id="div4">I am Div 4</div>
<div class="selectedDiv" id="div5">I am Div 5</div>
<input type="hidden" id="hfDivSelection" runat="server" />
<asp:Button runat="server" ID="buttonSave" OnClick="buttonSave_OnClick" Text ="Save" OnClientClick="GetSelection()"/>
</form>
<script type="text/javascript">
$('div').click(function () {
var css = $(this).attr('class');
if (css == 'selectedDiv') {
$(this).attr('class', 'deselectedDiv');
} else {
$(this).attr('class', 'selectedDiv');
}
});
function GetSelection() {
$('div').each(function() {
var values = $('#<%=hfDivSelection.ClientID%>').val();
var css = $(this).attr('class');
var divId = $(this).attr('id');
if (css == 'selectedDiv') {
$('#<%=hfDivSelection.ClientID%>').val(values + divId + ':true;');
} else if (css == 'deselectedDiv') {
$('#<%=hfDivSelection.ClientID%>').val(values + divId + ':false;');
}
});
}
</script>
</body>
</html>
Code Behind :
protected void buttonSave_OnClick(object sender, EventArgs e)
{
foreach (var selectedDiv in this.hfDivSelection.Value.Split(';'))
{
var divId = selectedDiv.Split(':')[0];
var divValue = selectedDiv.Split(':')[1];
// Perform action on divId and divValue
}
}

I recommend the $.ajax function of jquery. It is very convenient.
Here is an example.
Javascript + jquery code:
//this $.ajaxSetup step is optional, but will save you a bunch of caching and asynchrony problems.
$.ajaxSetup({
cache: false,
async: false
});
$.ajax({
type: "POST",
url: 'submit.aspx',
data: {"field1": "value1", "field2": "value2"},
dataType: 'json',
success: function(response){console.log('Data submit worked. Response was:\n' + response)}
});
(More info on this function at http://api.jquery.com/jQuery.ajax/.)
Then, in submit.aspx, place your code to get the info, this SO article may help.
You can then save the data to an xml file via asp.net. When you want to reload the user's settings, you can use the GET command of the $.ajax function:
$.ajax({
type: "GET",
url: '/data/userfields.xml',
dataType: "xml",
success: function(xml) {
var fieldvalue = $(xml).find('a_node').attr('an_attrib');
//...
},
error: function(xml) { console.log ('failed to get xml file on import of file: /data/userfields.xml');}
});

In my opinion the best thing would be to use checkboxes (placed in a form that will be submited on button click) and use CSS to stile the div's accordig to the checkbox statuses.

I suggest using ajax callbacks. Using cookies on this approach is a bit messy. Create "on click" events on each div and if you really want to use a best practice approach to save data on the client side I suggest using Local Storage:
http://www.w3schools.com/html/html5_webstorage.asp
Hope this helps

Related

Dynamically loaded content through $.post not retaining click events

So, I'm trying to create a TODO list but I'm having problems with "click" events once I dinamically load content.
What I want to achieve is that, once I click an element, send the "id" through $.post to a PHP file that deletes said row from my MySQL Database. And then, shows a new list without the deleted row.
Currently, I'm loading my "list.php" with $.get onto my "#todo-list" div. However, once I click, the info is sent, the row gets deleted, I get the new list without the deleted element. Every is ok at that point.
However, when I click an element of my new list, nothing happenns.
This is my Javascript File:
$(function() {
$.get("list.php", function(data){
$("#todo-list").html(data);
$("#todo").on("click", "li", function(){
let li = $(this);
let id = li.attr("id");
$.post("list.php", {id: id}, function(data){
$("#todo-list").html(data);
});
});
});
});
Here is my HTML page:
<html>
<head>
<title>My test app</title>
<script src="https://code.jquery.com/jquery-3.4.0.min.js"></script>
<script src="./script.js"></script>
<style>
.todo-list li:hover {
text-decoration: line-through;
}
</style>
</head>
<body>
<h1>TODO: Just a list with stuff to do...</h1>
<div id="todo-list">
Loading content...
</div>
</body>
</html>
And this is my PHP file:
// code to connect to MySQL with PDO...
if ($_POST) {
// code to delete the id
}
$data = $pdo->prepare("SELECT * FROM todo");
$data->execute();
echo "<ul id='todo'>\n";
while ($row = $data->fetch()) {
echo "<li id='{$row['id']}'>{$row['todo']}</li>\n";
}
echo "</ul>\n";
As said, nothing happens after I get the new list with the deleted row.
I want my new list to be clickable, the same way the first list is... and of course, if I have 20 elements, I want to be able to click and delete them without reloading the page. Is it possible?
your click hanlder to delete row should be like this,you need to assign event handler again to newly added rows,
function delete_row(){
let li = $(this);
let id = li.attr("id");
$.post("list.php", {id: id}, function(data){
$("#todo-list").html(data);
//assigne the event handle again
$("#todo").on("click", "li",delete_row)
});
}
$(function() {
$.get("list.php", function(data){
$("#todo-list").html(data);
$("#todo").on("click", "li",delete_row)
});
});

Using basic jQuery append function, how would you put user-submitted text into it?

function createPost(){
$('#body').append("<p>Welcome to calmspace.</p>");
}
How would I utilize user input so the user can create a post with their own message? I am a newbie with jQuery so if this is a stupid question please forgive me. Possible duplicate but I couldn't find another post like this.
First things first - you should not have added '#' in front of body, it'd mean that the body element is of id 'body', assigning id to an element that is unique does not bear that much sense, instead you should just target the tag - $('body').
In order to provide some sort of message you first have to capture it, for instance using some sort of input. Here is a working demo.
$('#submit').click(function(){
createPost($('#text').val());
})
You read it as follows, grab element of id 'submit', assign it a click event, grab the value of input box of id 'text' and pass it to a function named create post which accepts a string parameter and then prints it in a <p> tag.
#Simion Benderschii a working example of a post which appends to the document or sends via ajax. Hope this helps
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<title>JS Bin</title>
</head>
<body>
<div>
<h2>Enter your post here</h2>
<form>
<textarea id='user-input-post'></textarea>
<div>
<button id=user-post-button>Post</button>
</div>
</form>
</div>
<div>
<h2>Below are your posts</h2>
<ul id='user-post-display'>
</ul>
</div>
</body>
<script>
/*possible options can be
'display' - which shows the post in the UI in a unordered list
'ajax' - which send the post to the server via ajax
*/
var post_type = 'display';
//the id of the list where the post will be appended
var list_id = '#user-post-display';
//the id where the post will be entered
var post_id = '#user-input-post';
//the id of the button which triggers some action
var button_id = '#user-post-button';
//this gets the post from the textarea
var get_post = function() {
var post = $(post_id).val();
return encodeURIComponent(post);
};
//this appends the post to the list
var append_post = function() {
var post = get_post();
var html_string = '';
if (post) {
html_string = '<li>' + post + '</li>';
$(list_id).append(html_string);
}
};
//this sends the post via ajax and triggers callbacks
var send_post = function() {
var post = get_post();
var post_created_on = Date.now();
var url = 'dummy_url_for_posting';
$.ajax({
method: 'POST',
url: url,
data: { data: {
post: post,
post_created_on: post_created_on
}}
})
.done(function() {
window.alert('post success');
})
.fail(function() {
window.alert('post fail');
})
.always(function() {
window.alert('post triggered');
});
}
//main function which is the entry point
var main = function() {
$(button_id).on('click', function() {
event.preventDefault();
debugger;
if (post_type === 'display') {
append_post();
} else if (post_type === 'ajax') {
send_post();
}
});
};
//triggers the main function
main();
</script>
</html>
I am not exactly sure what you want to do from your question. In future questions you will find it helpful to provide more detail on exactly what you want to do with your application or function.
The basic idea here is to use a button or any action you can capture with jQuery (like pressing enter or checking $(element).on('click',... and then putting that info where you want using $(element).html(...) or .append(...).
Here is a fiddle I made with the rough idea. Try to use this fiddle tool a lot, and you can also post the link to what you have tried in future questions. Good luck :-)
JSFiddle example of submitting a post

how to get textarea input from another HTML page

In a.html:
I have a textarea that is converted into a link after the user clicks the submit button. When the user clicks on the link they are redirected to b.html.
<textarea id="sentenceId">
</textarea>
<br>
<button type="button" id="buttonId" onclick="createLink(document.getElementById('sentenceId').value)">Submit
</button>
<p id="demo">
<a id ="link" href="b.html"></a>
</p>
In b.html:
I would like to display the original text.
In script.js:
function createLink(val) {
document.getElementById("link").innerHTML = val;
document.getElementById('buttonId').style.display = 'none';
document.getElementById('sentenceId').style.display = 'none';
}
If you want to open a new page and get the text there, you could use a post-form and an input[type="hidden"] to send the text and display it afterwards.
If you wand the link to be sendable, you'd either have to encode the text as get-parameter or save it to a database and add the id of the entry to the link.
As #Kramb already mentioned, localStorage is a possibility, but only if you stay on the same browser and both pages have the same domain.
Using localStorage
The localStorage property allows you to access a local Storage object. localStorage is similar to sessionStorage. The only difference is that, while data stored in localStorage has no expiration time, data stored in sessionStorage gets cleared when the browsing session ends—that is, when the browser is closed.
a.html
function createLink(val) {
document.getElementById("link").innerHTML = val;
document.getElementById('buttonId').style.display = 'none';
document.getElementById('sentenceId').style.display = 'none';
localStorage.setItem("textArea", val);
}
b.html
function getText(){
var textVal = localStorage.getItem("textArea");
}
Another option would be to use a query string.
a.html
function navigateTo(val){
window.href.location = "b.html?text=" + val;
}
This will pass the value of the text from textarea with the url during navigation. Once b.html has loaded, you can do the following.
b.html
function getText(){
var url = window.location.href;
var queryIndex = url.indexOf("=") + 1;
var passedText = url.substring(queryIndex);
document.getElementById('foo').value = passedText;
}
This is possible using JavaScript. You can do an AJAX call to another page on you website, and search for an element to get its content. In you're case an textarea
I wrote an example on codepen.io for you. Click here
To make things simpler im using jQuery in this example.
So how does it work?
First of, include jQuery inside the <head> tag of you're website.
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
I created the following structure
structure
root
scripts
jQuery.min.js
index.js
index.html
textarea.html
Contents of index.html
<!DOCTYPE html>
<html lang="en">
<head>
<!-- Meta -->
<meta charset="UTF-8" />
<title>My New Pen!</title>
<script type="text/javascript" src="scripts/jquery.min.js"></script>
<!-- Styles -->
<link rel="stylesheet" href="styles/index.processed.css">
</head>
<body>
<button id="clickme">To load the textarea content, click me!</button>
<div id="content">The data from the textarea will be shown here, afte you click on the button :)</div>
<!-- Scripts -->
<script src="scripts/index.js"></script>
</body>
</html>
Contents of texarea.html
<textarea id="textarea">
I am the content of the textarea inside the textarea.html file.
</textarea>
Contents of index.js
(function() {
$(document).ready(function() {
/**
* The button which triggers the ajax call
*/
var button = $("#clickme");
/**
* Register the click event
*/
button.click(function() {
$.ajax({
url: "textarea.html",
type: "GET"
}).done(function(response) {
var text = $(response).filter("#textarea").html();
$("#content").append("<br/><br/><strong>" + text + "</strong>");
});
});
});
})()
So what does index.js do exactly?
As you can see i created an Ajax call to the textarea.html file. The .done function holds the response data. The data inside it can be anything depending on the content of the textarea.html file.
$(response).filter("#textarea").html();
The above piece of code filters out the #textarea div and then gets the innerHTML using the jQuery html() function.
If you want to get the value of the textarea through the [value] attribute, you can replace above line to
$(response).filter("#textarea").val();
I believe you want to do this:
function createLink() {
var textvalue = document.getElementById('sentenceId').value;
document.getElementById("link").innerHTML = textvalue;
document.getElementById("buttonId").className ="hideme";
document.getElementById("sentenceId").className ="hideme";
}
.hideme{
display: none;
}
<textarea id="sentenceId">
</textarea>
<br>
<button id="buttonId" onclick="createLink()">Submit
</button>
<p id="demo">
<a id ="link" href="b.html"/>
</p>

jQuery load(URL) not working when loading page-fragments?

I have this page, the first button is working good.
I want when press the second button to give me the link that is in the href, i tried like this , but i got the whole page , not just the value of the link , why please?
<html>
<head>
<script src="jquery.js"></script>
<script type="text/javascript">
$(document).ready(function(){
var url = "http://localhost/test/asdfasdf.php";
$("#button").on("click", function() {
$('body').load( url );
});
$("#button2").on('click',function(){
$('body').load( url +"#link" );
});
});
</script>
</head>
<body>
<input type="button" id="button" value="load" />
<input type="button" id="button2" value="search for a tag" />
</body>
</html>
I think you want a space:
$('body').load(url + " #link");
http://api.jquery.com/load/#loading-page-fragments
All you seem to want is the href of the a#link element at that URL. So instead of loading it into the <body>, just make the AJAX request, and look through the result:
$.ajax({
type: "GET",
url: "http://localhost/test/asdfasdf.php",
dataType: "html"
}).done(function (data) {
var the_link = $(data).find("#link");
alert(the_link.attr("href"));
});
And to put the href in the <body>, add this line in the .done() method:
$("body").html(the_link.attr("href"));
// or
$("body").append(the_link.attr("href"));
But if you actually want to load the a#link element into <body>, do what you had before, but then look for the a#link element and get its attribute:
$('body').load(url + " #link", function () {
var the_link = $("#link");
alert(the_link.attr("href"));
});
EDIT
You're trying to capture the href of the <a> on a different page. A try:
$.get(url+' #link', function(data) {
var $link = $(data).find('a').attr('href');
alert($link);
});
That is my very best guess, but its a shot in the dark.
Currently your code evaluates to .load('http://localhost/test/asdfasdf.php#link'), where #link is a useless fragment. You need a space to engender jQuery's special behavior of automatic DOM parsing and element loading.
$("body").load(url + " #link");
EDIT: to get the actual link value:
$.get(url).done(function (html) {
console.log($(html).find('#link').attr('href'));
});
You can also append to body inside of the .done callback.

How to code one jquery function for all AJAX links

I am using zend framework on windows. I want to implement ajax in my project first time. I searched for help and created a very simple ajax functionality.
IndexController.php
public function indexAction() {
}
public function oneAction() {
}
public function twoAction() {
}
index.phtml
<script type="text/javascript" src="js/jquery-1.4.2.js"></script>
<script type="text/javascript" src="js/AJAX.js"></script>
<a href='http://practice.dev/index/one' class='one'>One</a>
<a href='http://practice.dev/index/two' class='two'>Two</a>
<br /><br />
<div id="one">one.phtml content comes here</div>
<div id="two">two.phtml content comes here</div>
AJAX.js
jQuery(document).ready(function(){
jQuery('.one').click(loadOne);
jQuery('.two').click(loadTwo);
});
function loadOne(event) {
event.preventDefault();
jQuery.ajax({
url: '/index/one',
success: function( data ) {
jQuery('#one').html(data);
}
});
}
function loadTwo(event) {
event.preventDefault();
jQuery.ajax({
url: '/index/two',
success: function( data ){
jQuery('#two').html(data);
}
});
}
Above code is working and loading data of one.phtml and two.phtml in 'one' and 'two' DIVs respectively when its link is clicked. You can see that I have to create separate jquery function for each link and also have to add new class for each link tag.
What I want to do ?:
I want to use only one jquery function for all AJAX requests and don't want to hard code url and success attributes in that function.
When I add "AJAX" class to any link tag then it should load content using AJAX.
Thanks.
for simple loading of data in divs i would use the load method
HTML
<script type="text/javascript" src="js/jquery-1.4.2.js"></script>
<script type="text/javascript" src="js/AJAX.js"></script>
One
Two
<br /><br />
<div id="one">one.phtml content comes here</div>
<div id="two">two.phtml content comes here</div>
JS
jQuery(document).ready(function(){
jQuery('.ajax').click(function(event){
event.preventDefault();
var target = '#' + jQuery(this).attr('rel');
var href = jQuery(this).attr('href');
jQuery( target ).load( href );
});
});
Use a single class to identify all links that should use ajax calls instead of their normal use. And add a rel attribute to those links that will contain the id of the container div..
Simple and Nice. No Jquery required. Check this out:
Bjax
Usage:
<script src="bjax.min.js" type="text/javascript"></script>
<link href="bjax.min.css" rel="stylesheet" type="text/css" />
Finally, include this in the HEAD of your html:
$('a').bjax();
For more settings, checkout demo here:
Bjax Demo
Maybe this:
function loadData(url, callback) {
jQuery.ajax({url: url, success: callback});
}
loadData('/index/one', function( data ) {
jQuery('#one').html(data);
})
loadData('/index/two', function( data ) {
jQuery('#two').html(data);
})
To make this even more compact you could define the same callback for both and then have the handler decide which element the response data should be written to.
Compact version:
$(function(){
$('.one').click(loadOne);
$('.two').click(loadTwo);
});
function loadOne(event) {
event.preventDefault();
$('#one').load('/index/one');
}
function loadTwo(event) {
event.preventDefault();
$('#two').load('/index/two');
}

Categories

Resources