I'm having troubles delaying the tab change when loading in content with ajax.
If I'm positioned in tab 0 and click on tab 1, I want the content to be loaded with ajax and when it's done, switch tab.
At the moment the tab is changed instant, which gives a blank side till my ajax content is loaded.
HTML:
<ul class="nav nav-tabs" id="tab" role="tablist">
<li class="active"><a data-toggle="tab" id="tab1" href="#container1">Information</a></li>
<li><a data-toggle="tab" id="tab2" href="#container2">Users</a></li>
</ul>
<div class="tab-content">
#*TAB1*#
<div class="tab-pane active" id="container1">
#Html.Partial("_StaticContentFromView")
</div>
#*TAB2*#
<div class="tab-pane" id="container2">
</div>
</div>
JS:
$('#tab2').click(function () {
$.ajax({
url: '/Home/Test',
type: 'GET',
dataType: 'html',
success: function (data) {
$('#container2').html(data);
}
});
});
Update 1:
$('a[data-toggle="tab"]').on('shown.bs.tab', function (e) {
e.target // activated tab
e.relatedTarget // previous tab
})
This event fires before tab is changed, so I can probably load the content here.
However this event is called everytime tab is changed. How can i check which tab is choosen?
e.target gives me a url, that is not good enough..
Alright found a way..
$('a[data-toggle="tab"]').on('show.bs.tab', function (e) {
var tabName = $(e.target).text(); //Get the name of the tab.
if (tabName == 'Users') {
$.ajax({
url: '/Home/Test',
type: 'GET',
async: false,
dataType: 'html',
success: function (data) {
$('#container2').html(data);
e.target // activated tab
e.relatedTarget // previous tab
}
});
}
})
It's important that you set async to false otherwise it wont work.
Related
I have a simple form that shows a modal popup upon ajax success. It works great the 2nd time its used in same session. The modal will never show on the first form submission. What could be causing the modal not to fire the first time around? Maybe the page refresh or form reset?
$(document).ajaxSend(function(event, request, settings) {
$('#loading-indicator').show();
$("#submitbtn").prop('disabled', true);
});
$(document).ajaxComplete(function(event, request, settings) {
$('#loading-indicator').hide();
$("#output").fadeTo(4000, 500).slideUp(500, function(){
$("#output").slideUp(500);
});
$("#myform")[0].reset();
$("#submitbtn").prop('disabled', false);
setTimeout(function(){// wait for 5 secs(2)
location.reload(); // then reload the page.(3)
}, 5000)
});
$(function () {
// init the validator
// validator files are included in the download package
// otherwise download from http://1000hz.github.io/bootstrap-validator
$('#myform').validator();
// when the form is submitted
$('#myform').on('submit', function (e) {
// if the validator does not prevent form submit
if (!e.isDefaultPrevented()) {
var url = "add_report.php";
var formData = new FormData($('#myform')[0]);
$.ajax({
url: 'add_report_do.php',
enctype: 'multipart/form-data',
type: 'POST',
data: formData,
success: function(response) {$("#successModal").modal("show");},
contentType: false,
processData: false,
cache: false
});
return false;
}
})
});
<div id="successModal" class="modal modal-blur fade" tabindex="-1" role="dialog">
<div class="modal-dialog modal-sm modal-dialog-centered" role="document">
<div class="modal-content">
<div class="modal-body">
<p>Fishing report successfully added.<br /></p>
</div>
<div class="modal-footer">
<button type="button" class="btn btn- btn-primary" data-dismiss="modal">OK</button>
</div>
</div>
</div>
Well I figured it out. require.js and jquery were stepping on each other. Added a line to require.config to isolate jquery. Works fine now
define('jquery', function () { return jQuery; });
There is a script that needs to update the data on the page in a specific div. But instead of updating, the block with the div is simply hidden and in order for it to appear again, you need to reload the page. The data comes in data, but here is $ ("# userPost" + id) .html (data); something doesn't work.
$.ajaxSetup({
headers: {
'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
}
});
$('.infinite-scroll').on('click', '#editPostButton', function(e) {
e.preventDefault();
var id = $(this).data('id');
var user_id = $('#userForm').val();
var form = document.getElementById('EditPostForm'+id);
var formData = new FormData(form);
// var formData = $('#EditPostForm'+id).serialize();
$.ajax({
url: "id"+user_id+"/"+id+"/edit",
type: "POST",
data: formData,
success: function(data) {
console.log(data);
$("#userPost"+id).html(data);
$("#closeButton"+id).click();
},
error: function() {
console.log('error');
},
processData: false,
contentType: false,
});
});
And div
<div id="userPost{{$post->id}}">
#if($post->img)
<div>
<img src="{{$post->img}}" class="img-fluid">
</div>
#endif
<br>
#if($post->title)
<div class=" mr-1 mb-3 titleleft">
<h5 style="color: black"><b>{{$post->title}}</b></h5>
</div>
#endif
#if($post->message)
<div class="text-muted text-small margins" style="white-space: pre-wrap;">{{mb_strimwidth($post->message, 0, 600, " . . . Read more")}}</div>
#endif
#if($post->videoPost)
<div class="embed-responsive embed-responsive-16by9 mt-4 mb-2">
<iframe class="embed-responsive-item" src="{{$post->videoPost}}" allowfullscreen></iframe>
</div>
#endif
</div>
Try doing this way:
$("#userPost"+id).load(url);
or
$("#userPost"+id).html(data).load(url);
I'm populating a folder structure using TreeView in .cs file, rendering it in the view.cshtml. When an item is clicked, I call a js function which makes an ajax call to the web api, gets the file content and supposed to display the result in a TextArea or Div.
The result comes back from web api, and displays it in the textarea momentarily and disappears. I guess it's refreshing the page. But I'm not sure how to prevent it. I have done similar stuffs before, didn't behave so. I'm sure I'm missing something, but I can't tell what I'm missing.
#{
Layout = "~/Views/Shared/_Layout.cshtml";
}
<form>
<div style="width: 100%; overflow: hidden;">
<div style="width: 600px; float: left;">
<ul>
#foreach (var node in Model.Nodes[0].ChildNodes)
{
<li>#node.Text</li>
<ul>
#foreach (var f in node.ChildNodes)
{
<li>#f.Text</li>
}
</ul>
}
</ul>
</div>
<div id="divLog" style="margin-left: 620px;overflow:auto;"><textarea id="txtLog" rows="10" cols="50"></textarea></div>
</div>
</form>
<script>
function getLog(fileref) {
var baseURL = window.location.protocol + '//' + window.location.host + '#Url.Content("~")';
var apiUrl = baseURL + "/api/logapi?fileref=" + fileref;
document.getElementById("txtLog").innerText = "";
$(document).ready(function () {
$.ajax({
url: apiUrl,
type: "GET",
success: function (data, textStatus, jqXHR) {
document.getElementById("txtLog").innerText = data;
//document.getElementById("txtLog").innerHTML = data;
//$("#txtLog").val(data);
alert(data);
}
});
});
}
</script>
Maybe another solution for any people coming here. I had the same issue in my Razor pages project when trying to call an Ajax function from a form. The page would call the correct page handler and return the Json result, however the page would always refresh, and the success part in the ajax call would not be called. What worked FOR ME was to REMOVE the form element and replace it with a div. Now the Ajax call returns correctly for me.
<div id="first" class="section"> //WHEN THIS WAS FORM THE PAGE REFRESHED
<div class="section">
#Html.HiddenFor(m => m.PersonId)
#Html.HiddenFor(m => m.ProviderId)
#Html.AntiForgeryToken()
<div class="container2">
<input type="radio" name="group1" id="radio-1" checked="checked">
<label for="radio-1"><span style="font-size:16px;" class="radio">I want to recieve all Emails (personal and marketing)</span></label>
</div>
<button onclick="setPreferences()" class="btn btn-save">Save <i class="fa fa-save"></i></button>
</div>
</div>
And the ajax:
$.ajax({
url: '/UserPreferences?handler=SetPreferences',
type: 'POST',
contentType: "application/json; charset=utf-8",
dataType: "json",
data: JSON.stringify(model),
headers: {
RequestVerificationToken: $('input:hidden[name="__RequestVerificationToken"]').val()
},
success: function (response) {
console.log(response);
}
});
I used button instead of anchor link, it works as expected, it doesn't refresh the screen.
<style>
.btn1 {
background-color: transparent;
border: hidden;
}
</style>
<li><input type="button" id="a" value="#f.Text" onclick="getLog('#f.Value')" class="button btn1"></li>
First, remove the Ajax call from the document ready function:
function getLog(fileref) {
var baseURL = window.location.protocol + '//' + window.location.host + '#Url.Content("~")';
var apiUrl = baseURL + "/api/logapi?fileref=" + fileref;
document.getElementById("txtLog").innerText = "";
$.ajax({
url: apiUrl,
type: "GET",
success: function (data, textStatus, jqXHR) {
document.getElementById("txtLog").innerText = data;
//document.getElementById("txtLog").innerHTML = data;
//$("#txtLog").val(data);
alert(data);
}
});
}
Secondly, replace the empty href attribute of the anchor link by href="javascript:;" or href="#".
I have a dashboard with some side menus. Each menus loads a page through ajax call after it is clicked.
By default when dashboard is loaded it loads the page, there is also a "dashboard" menu to switch between others like profile and add student.
But if I am at profile page and I refresh It goes back to dashboard page. Also if I try to add student by filling the form and if the form has any error it goes back to dashboard again with all old input data lost.
Web.php
Route::prefix('admin')->group(function(){
Route::get('/dashboard','AdminController#dashboard')->name('admin.dashboard');
Route::get('/login', 'Auth\AdminLoginController#showLoginForm')->name('admin.login');
Route::post('/login', 'Auth\AdminLoginController#login')->name('admin.login.submit');
Route::post('/add_student','AdminController#add_student');
Route::middleware('ajax')->group(function(){
Route::get('/summary','AdminController#summary')->name('admin.summary');
Route::get('/profile', 'AdminController#profile')->name('admin.profile');
Route::get('/add_student_form','AdminController#add_student_form')->name('admin.add_student');
});
});
AdminController.php
public function add_student_form(){
return view('admin.add_student');
}
public function add_student(Request $request)
{
$this->validate($request,[
'name'=>'required|string',
'course_id'=>'required',
'dob'=>'required|date',
'gender'=>'required|string',
'category'=>'required|string',
'qualification'=>'required|string',
'fathername'=>'required|string',
'mothername'=>'required|string',
'mob_no'=>'required|string|max:10',
'address'=>'required|string',
'email'=>'required|email',
'PIN'=>'required|string|max:6',
]);
$student = new Student;
$student->name = $request['name'];
$student->roll_no ='NITTI'.rand(10000,99999);
$student->password = Hash::make($student['mob']);
$student->fees = new StudentFees;
$student->fees->paid_fees = $request['paid_fees'];
$student->fees->balance_fees = 7000;
$student->detail = new StudentDetail;
$student->detail->course_id = $request['course_id'];
$student->detail->gender = $request['gender'];
$student->detail->category = $request['category'];
$student->detail->qualification = $request['qualification'];
$student->detail->fathername = $request['fathername'];
$student->detail->mothername = $request['mothername'];
$student->detail->mob_no = $request['mob_no'];
$student->detail->email = $request['email'] ;
$student->detail->address = $request['address'];
$student->detail->PIN=$request['PIN'];
$student->detail->dob = $request['dob'];
$student->push();
return redirect()->back();
}
add_student.blade.php
<form action="/admin/add_student" method="POST">
#csrf
//It has all the fields here and a submit button
</form>
dashboard.blade.php
<div class="container-fluid">
<div class="row">
<div class="col-2 sidebar">
<img src="{{asset('/img/admin.jpg')}}" class="fit-image">
<p class="text-center">{{Auth::user()->name}}</p>
<hr>
<ul class="list-group">
<li class="list-group-item" id="summary">Dashboard</li>
<li class="list-group-item" id="admin_profile">Profile
</li>
<li class="list-group-item" id="students">Students <i class="fas fa-angle-right ml-5"></i>
<ul class="sidenav list-group">
<li class="list-group-item" id="add_student">Add Student</li>
<li class="list-group-item" id="viewall">View All </li>
</ul></li>
</ul>
</div>
<div class="col-10 dashboard" id="admin">
</div>
</div>
</div>
dashboard.js
$(document).ready(function(){
$.ajax({
url:'/admin/summary',
type: "GET",
success: function(data){
$data = $(data);
$('#admin').html($data).fadeIn();
}
});
});
$(document).on('click','#summary', function(){
$.ajax({
url:'/admin/summary',
type: "GET",
success: function(data){
$data = $(data);
$('#admin').html($data).fadeIn();
}
});
});
$(document).on('click','#admin_profile', function(){
$.ajax({
url:'/admin/profile',
type: "GET",
success: function(data){
$data = $(data);
$('#admin').html($data).fadeIn();
}
});
});
$(document).on('click','#add_student', function(){
$.ajax({
url:'/admin/add_student_form',
type: "GET",
success: function(data){
$data = $(data); produced
$('#admin').html($data).fadeIn();
}
});
});
I tried to redirect()->back->withInput('the fields');, but it didn't work.
If there is better way to load the pages which holds the same page after reloading or form submission I would welcome that.
You could use ajax form posting.
I rewrote code to abstract ajax load.
JS:
$(document).ready(function(){
//load summary by default
loadPage('summary');
//load on click menu item
$(document).on('click','.menu-item', function(){
loadPage($(this).attr('data-page'));
});
//send xcrf token in ajax header
$.ajaxSetup({
headers: {
'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
}
});
//submit form
$(document).on('submit', 'form', function(){
let form = $(this);
$.ajax({
url: form.attr('action'),
type: 'POST',
dataType: 'json',
success: function(data){
if(data.page){
//load page returned in controller
loadPage(data.page);
}
},
error: function(data){
if(data.responseJSON && data.responseJSON.errors){
$.each(data.responseJSON.errors, function(key, value){
//convert laravel dotted rules to jquery selectors
key = key.replace('.', '[').replace(/\./g, '][');
if(key.indexOf('[') !== -1){
key += ']';
}
//do something with errored elements
form.find('*[name="' + key + '"]').addClass('error');
});
}
}
});
return false;
});
});
function loadPage(page){
$.ajax({
url:'/admin/' + page,
type: 'GET',
success: function(data){
$data = $(data);
$('#admin').html($data).fadeIn();
}
});
}
HTML:
Add to <head>:
<meta name="csrf-token" content="{{ csrf_token() }}">
Change sidebar menu:
<ul class="list-group">
<li class="list-group-item menu-item" data-page="summary">Dashboard</li>
<li class="list-group-item menu-item" data-page="profile">Profile</li>
<li class="list-group-item" id="students">Students <i class="fas fa-angle-right ml-5"></i>
<ul class="sidenav list-group">
<li class="list-group-item menu-item" data-page="add_student_form">Add Student</li>
<li class="list-group-item menu-item" data-page="viewall">View All </li>
</ul>
</li>
</ul>
Controller method:
Replace return redirect()->back(); with return ['page' => 'viewall'];
Currently Developing web Application using AngularJS using with Kendo. When I save inline edit grid need to hide my save button and want to show back the Add button. For Show and Hide I use *ngIf. In this class I define public isAddEdit: Boolean; I cannot access the variable in success scope.
update: function (options) {
$.ajax({
url: HttpUrl.UpdateBlog,
contentType: "application/JSON",
type: "POST",
data: JSON.stringify(options.data.models),
success: function (result) {
options.success(result);
this.isAddEdit = false;
$('#save').remove();
$('#grid').data('kendoGrid').dataSource.read();
},
})
This is my view
<div id ="btndiv" class="col-sm-12">
<button *ngIf="!isAddEdit" id="addblog" class="k-button grid-top-button-override k-primary add-button page-name" (click)="addStock()">{{'Addblog' | translate}}</button>
<button *ngIf="isAddEdit" id ="save" class="k-button grid-top-button-override k-primary save-button page-name" (click)="clicksave()">{{'Save' | translate}}</button>
</div>
<div class="row grid-override">
<div id="grid"></div>
</div>
I think that the this is related to the AJAX callback function therefore you are not accesing the variable you want.
Try it with an arrow function:
success:(result) => {
options.success(result);
this.isAddEdit = false;
$('#save').remove();
$('#grid').data('kendoGrid').dataSource.read();
},