How to access implicit objects in my templates - servlets

I want to know what is the current url of my template. I have read here that the "request" is an implicit object present in all templates which returns the url of my template.
So I have tried this:
Controllers:
public class Application extends Controller {
public static Result index() {
return redirect("/home");
}
public static Result home() {
return ok(homePage.render());
}
public static Result aboutUs() {
return ok(aboutUs.render());
}
}
HTML:
leftbar.scala.html file:
<aside id="left-panel">
<nav>
<ul class="animated fadeInLeft">
<li class="#if(request.uri.contains("/aboutus")){active}">(some code here)</li>
</ul>
</nav>
</aside>
homePage.scala.html file:
#scripts = { (some scripts here) }
#views.html.main("Beta Project", scripts) {
#views.html.leftbar()
<div id="main" role="main">
<div id="content">
<span><i class="fa fa-bell"></i>SOMETHING</span>
</div>
</div>
}
Where I import the leftbar.scala.html file I get this error:
not found: value request
What should I do to solve this error? Thanks in advance

A bit more code from your template would be useful, but you can probably fix it by adding
(implicit request: Request[AnyContent])
at the end of the first line on your template.

Related

ASP.Net Core MVC - Validation Summary not working with bootstrap tabs and dynamically loaded content

How do you get dynamically loaded tabs to work in ASP.Net Core MVC?
I have a simple Index.cshtml that uses bootstrap tabs to create two tabs from the a tags on the page. (To test out options, I first copied from https://qawithexperts.com/article/asp.net/bootstrap-tabs-with-dynamic-content-loading-in-aspnet-mvc/176)
There is a click event on each tab that uses $.ajax() to call the controller and then set the html of the appropriate div.
I have a model with one field, a string that is required.
I have the create view that Visual Studio created.
When I run it and click the first tab, the controller returns PartialView("FirstTabCreate") and loads into the div and everything looks great.
The problem is when clicking the "Create" button.
The controller method checks if IsValid on the ModelState. If not, here is where I run into a problem. If I return the partial view and the model that was passed in I see my validation errors as expected but because I returned the partial view, I lose my tabs. If I return the main view (Index) then the javascript reloads my partial view and has lost the ModelState at that point.
I am not sure what to return so that this works. I have seen lots of examples online that use dynamically loaded tabs but none of them have models or validation.
Code below:
Index Page
#model FirstTab
<!-- Tab Buttons -->
<ul id="tabstrip" class="nav nav-tabs" role="tablist">
<li class="active">
Submission
</li>
<li>
Search
</li>
</ul>
<!-- Tab Content Containers -->
<div class="tab-content">
<div class="tab-pane active" id="FirstTab">
</div>
<div class="tab-pane fade" id="SecondTab">
</div>
</div>
<script src="~/lib/jquery/dist/jquery.min.js"></script>
<script>
$('#tabstrip a').click(function (e) {
e.preventDefault();
var tabID = $(this).attr("href").substr(1);
$(".tab-pane").each(function () {
console.log("clearing " + $(this).attr("id") + " tab");
$(this).empty();
});
$.ajax({
url: "/#ViewContext.RouteData.Values["controller"]/" + tabID,
cache: false,
type: "get",
dataType: "html",
success: function (result) {
$("#" + tabID).html(result);
}
});
$(this).tab('show');
});
$(document).ready(function () {
$('#tabstrip a')[0].click();
});
</script>
FirstTabCreate View
#model WebApplication1.Models.FirstTab
<h4>FirstTab</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="FirstTabCreate">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="FirstName" class="control-label"></label>
<input asp-for="FirstName" class="form-control" />
<span asp-validation-for="FirstName" class="text-danger"></span>
</div>
<div class="form-group">
<input type="submit" value="Create" class="btn btn-primary" />
</div>
</form>
</div>
</div>
<div>
<a asp-action="Index">Back to List</a>
</div>
Model
using System.ComponentModel.DataAnnotations;
namespace WebApplication1.Models
{
public class FirstTab
{
[Required()]
public string FirstName { get; set; }
}
}
Controller
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging;
using System.Diagnostics;
using WebApplication1.Models;
namespace WebApplication1.Controllers
{
public class HomeController : Controller
{
public IActionResult Index()
{
return View();
}
public ActionResult FirstTab()
{
return PartialView("FirstTabCreate");
}
public ActionResult FirstTabCreate(FirstTab model)
{
if (!ModelState.IsValid)
{
return View("FirstTabCreate", model);
}
return Content("Success");
}
public ActionResult SecondTab()
{
return PartialView("_SecondTab");
}
}
}
I don't like it but to get it to work, when I click Save, in the Controller method I check if the ModelState is valid. If not, I put the keys and values into a list of custom class and then put that list in the cache. When the child partial view loads it checks to see if there is anything in the cache and if so, parses it back out and uses ModelState.AddModelError().
It's not pretty but it does allow the validation to work.
try to add jquery validation scripts in your code
delete this
<script src="~/lib/jquery/dist/jquery.min.js"></script>
and use this instead
#section Scripts {
#{await Html.RenderPartialAsync("_ValidationScriptsPartial");}
}
Add below code to your #section Scripts
#section Scripts {
#{await Html.RenderPartialAsync("_ValidationScriptsPartial"); }
<script>
$.validator.setDefaults({
ignore: []
});
</script>
}
Note: do not add the above inside $(document).ready()

How can I change the attribute in header section of cshtml files?

I have a problem about removing attributes when I navigate pages.
I used PartialView in HomeController to define index.cshtml page.
The line which I pass the data to the destination is showed orderly.
HomeController -> Contract.cshtml -> _Layout.cshtml -> NavbarPartial.cshtml
Here is HomeController.cs file shown below.
public ActionResult ContractUs()
{
ViewBag.Attribute = ""; // header-transparent
return View();
}
Here is my Contract.cshtml shown below.
#{
ViewBag.Title = "Contract Us";
Layout = "~/Views/Shared/_Layout.cshtml";
}
Here is my _Layout.cshtml shown below.
Html.RenderAction("NavbarPartial", "Home");
Here is my NavbarPartial.cshtml shown below.
<header id="header" class="fixed-top d-flex align-items-center header-transparent">
</header>
What I want to do is to show this header code snippet in the index page and show another one on another page like this shown as below without changing NavbarPartial.cshtml.
Index.cshtml
<header id="header" class="fixed-top d-flex align-items-center header-transparent">
</header>
Contract.cshtml
<header id="header" class="fixed-top d-flex align-items-center">
</header>
How can I do that?
If you render your partial view from another view, then you can send some parameters to decide what class should be applied. So let's look at the example.
We call partial view and send additional data:
#{Html.RenderPartial("_Header", new ViewDataDictionary { { "ApplyStyle", true } });}
and then in partial view we can apply style conditionally:
#{
var yourClasses = "";
if ((bool)ViewData["ApplyStyle"])
{
yourClasses = "fixed-top d-flex align-items-center header-transparent";
}
else
{
yourClasses = "fixed-top d-flex align-items-center";
}
}
<header id="header" class="#yourClasses">
This is header!
</header>
UPDATE:
This is a fiddle with complete example. However, this fiddle does not support PartialView, but I believe basic idea is shown.
Try using conditions in class value.
For example:
<header id="header" class="fixed-top d-flex align-items-center #(#Model.name === 'index' ? 'header-transparent' : '')">
If you dont have any kind of variable name for current component, you can use Javascript's location object.
window.location.pathname will provide you the pathname of current page.
Using this value you can add conditional class values

Illegal characters in path in Html.RenderAction

I am trying to call child action from view as below
#{
Html.RenderAction("Render", "ProgressBar", new { total = 10, completed = 3 });
};
and my controller code is as below
public class ProgressBarController : Controller
{
// GET: ProgressBar
[ChildActionOnly]
public ActionResult Render(int total, int completed)
{
ViewBag.Total = total;
ViewBag.Completed = completed;
ViewBag.Percent = ((completed * 100) / total).ToString("0.#####");
return PartialView();
}
}
and partial view for Render
<div class="section-progress-wrapper">
<div class="section-progress-info clearfix">
<div class="section-progress-label float-l">
<span class="section-progress-output">#ViewBag.Completed</span>
<span class="section-progress-desc">of</span>
<span class="section-progress-total">#ViewBag.Total</span> modules completed
</div>
<div class="section-progress-icon float-r"></div>
</div>
<div class="section-progress-box">
<div id="progressBar" class="section-progress-range" style="width:#string.Format("{0}%",ViewBag.Percent)"></div>
</div>
</div>
but for some reason I am getting exception saying
System.ArgumentException: Illegal characters in path.
I am not able to figure out what I am doing wrong. Can someone please help?

Pulling Single Quote From DB and displaying on page using Laravel

I have some quotes in a database and am trying to use Laravel to display it on a page. I have the quotes being pulled from the controller then passed to the view but I am getting an error:
Undefined variable: quotes (View: C:\laragon\www\resources\views\inc\quote.blade.php) (View: C:\laragon\www\\resources\views\inc\quote.blade.php) (View: C:\laragon\www\\resources\views\inc\quote.blade.php
QuotesController.php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;
use App\Http\Controllers\Controller;
class QuotesController extends Controller
{
public function index()
{
$quotes = DB::table('quotes')->get();
return view('inc.quote', ['quotes' => $quotes]);
}
}
quote.blade.php
<div id="MarketingQuote" class="container-fluid padding bg-light">
<div class="row">
<div class="col-lg-6">
<h2>Marketing Quote of the day</h2>
#foreach($quotes->all() as $quote)
<li>{{$quote}}</li>
#endforeach
<br>
</div>
<div class="col-lg-6">
<img src="img/computer.jpg" class="image-fluid" alt="">
</div>
</div>
</div>
Migration Table for Quotes
<?php
use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;
class CreateQuotesTable extends Migration
{
public function up()
{
Schema::create('quotes', function (Blueprint $table) {
$table->bigIncrements('id');
$table->text('quote');
$table->string('author');
$table->timestamps();
});
}
public function down()
{
Schema::dropIfExists('quotes');
}
}
Why do I get this error? And how do I get only one quote to display at a time and only change upon each page refresh?
Thank you.
I advise you to input the variable $quotes in the controller, And I remember the passed variable array key which can use and not have to use all function.
The below code from laravel manual:
Route::get('greeting', function () {
return view('welcome', ['name' => 'Samantha']);
});
Hello, {{ $name }}.
change
#foreach($quotes->all() as $quote)
<li>{{$quote}}</li>
#endforeach
into
#foreach($quotes as $quote)
<li>{{$quote}}</li>
#endforeach

UseThymeleaf template view with retrieve data from database to another template view

I'm trying to include the view service which already retrieve data from my database to my index.html page. I'm using Spring and Thymeleaf.
This is my service controller
#Controller
public class MyServicesController{
#Autowired
private ServicesForOurServices servicesForOurServices;
#RequestMapping(value = "myservices",method = RequestMethod.GET)
public String myServices(Model model){
model.addAttribute("services",servicesForOurServices.listAll());
return "services";
}
#RequestMapping(value = "services",method = RequestMethod.GET)
public ModelAndView listAll() {
ModelAndView modelAndView = new ModelAndView("services");
modelAndView.addObject("services",servicesForOurServices.listAll());
return modelAndView;
}
#ModelAttribute("services")
public Iterable<MyServices> services() {
System.out.println("Inside service without model");
return servicesForOurServices.listAll();
}
}
And my service template view
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head lang="en">
<title>Services</title>
<!--/*/ <th:block th:include="fragments/headerinc :: head"></th:block> /*/-->
</head>
<body th:fragment="services">
<!--/*/ <th:block th:include="fragments/header :: header"></th:block> /*/-->
<div th:if="${not #lists.isEmpty(services)}" class="container-fluid text-center" id="services">
<h2>SERVICES</h2>
<h4>What we offer</h4>
<div th:each="service : ${services}">
<div class="col-sm-4">
<span th:class="${service.getIcon()}"></span>
<h4 th:text="${service.getName()}"></h4>
<p th:text="${service.getDescription()}"></p>
</div>
</div>
</div>
</body>
</html>
Then I include the fragment to my index.html
<!--/*/ <th:block th:include="services :: #services"></th:block> /*/-->
But the index.html only render the h2 and h4 tag and not the div containing the services
and if I access the services.html everything renders fine
Thanks in advance
Have you inspect the elements from your browser to see whether there is any error fetching pictures? Suspecting the URL is incorrect after rendering.

Resources