How to hide specific jqueryui tab based on some condition? - c#

I am working on an application in which a selected tab should not visible to specific users.My code is
<div id="tabs">
<ul>
<li>Log Tickets</li>
<li>Open Tickets</li>
</ul>
<div id="divLogTickets" runat="server" style="padding: 25px;">
</div>
</div>
if (getUserRole(Convert.ToString(Session["UserId"])) == "HR")
{
//hide tab
}
How to hide a specific tab based on specific user role.

You can add id and runat="server" attributes to the elements that you want to access from the code behind and set the .Visible property in code behind.
For example if you want to hide Log Tickets tab, here's what your aspx code should look like:
<div id="tabs">
<ul>
<li id="liLogTickets" runat="server">Log Tickets</li>
<li>Open Tickets</li>
</ul>
<div id="divLogTickets" runat="server" style="padding: 25px;">
</div>
</div>
Then set the visibility of liLogTickets and divLogTickets in code behind:
if (getUserRole(Convert.ToString(Session["UserId"])) == "HR")
{
//hide Log Tickets tab
liLogTickets.Visible = false;
divLogTickets.Visible = false;
}

You can use $(selector).hide(); method hide.
For eg:
if (getUserRole(Convert.ToString(Session["UserId"])) == "HR")
{
//hide tab
$('#userId').hide();
}

After the validations , i.e. you have validated that this particular user you want to hide it from (as you have mentioned in your code) further you can use the hide() function to hide that particular element.
$('#Id_of_Element').hide();

Related

Blazor Dropdown with Search field - Handle Onfocusout

I have a dropdown with a search field to filter the list. Here is the basic structure:
<div class="dropdown">
<button class="dropdown-button dropdown-toggle" #onclick="e => this.show = !this.show"></button>
<div class="dropdown-menu #(show ? "show" : "")">
<input class="form-control form-control-sm" placeholder="type filter..."/>
<div class="scrollable-menu">
<table>
...
</table>
</div>
</div>
</div>
How do I hide the dropdown when the user clicks somewhere else?
If I use the onblur event of the button the dropdown gets hidden when the user clicks inside the filter input --> doesnt work.
The dropdown-menu is outside the dropdown div so I can't use that.
It would be ideal if I could group the button and the dropdown list together somehow so that the focusout event only gets triggered when the user clicks outside this "group" of elements.
EDIT
I updated the code snipped to show where how I toggle the dropdown.
The show variable is also inverted when the user selects an element in the list.
The simplest way is to use CSS - hide the scrollable-menu by default, then display it when anything in the dropdown has focus.
.scrollable-menu {
display: none;
}
.dropdown:focus-within .scrollable-menu {
display: block;
}
Edit: Add more complicated Blazor event based version
This problem (which I had not understood fully before) is usually solved in javascript detecting whether the target element of a focus change is within the container, but that then means interop calls to set/update your show field.
A purely Blazor solution could be handled by delaying the hide and cancelling if focus remains inside.
<div class="dropdown">
<button class="dropdown-button dropdown-toggle" #onclick=HandleClick #onfocus=HandleFocus #onblur=HandleBlur ></button>
<div class="dropdown-menu #(show ? "show" : "")" #onfocusin=HandleFocus #onfocusout=HandleBlur tabindex="-1">
<input class="form-control form-control-sm" placeholder="type filter..."/>
<div class="scrollable-menu">
<table>
...
</table>
</div>
</div>
</div>
#code{
bool show;
CancellationTokenSource tokenSource;
void HandleClick() => show = !show;
async Task HandleBlur(FocusEventArgs a)
{
tokenSource = new CancellationTokenSource();
await Task.Factory.StartNew(async ()=> {
await Task.Delay(100);
show = false;
await InvokeAsync(StateHasChanged);
},tokenSource.Token);
}
void HandleFocus(FocusEventArgs a)
{
if (tokenSource is CancellationTokenSource)
tokenSource.Cancel();
}
}
Try it out here: https://blazorrepl.com/repl/wFESlpaa33iocZJR52
use InvokeVoidAsync. It will not work if you make it async.
#onclick="#(e => {
JsRuntime.InvokeVoidAsync("eval",$"bootstrap.Dropdown(yourID).toggle()");
})"

Hiding a button inside a div from code

I have a aspx page and i want to hide the button from cs file based on my some condition
My .aspx looks like :
<asp: Content Id="contentid" >
<% if (!IsRedeemCardFlowOptin)
{ %>
<ul id="ulid" class="abc">
</ul>
<div class="bcd" id ="div1">
<div id="div2"></div>
<div id="div3"></div>
<div id="div4" runat="server">
<h4><%= m_AutoRenewInfo.NewPageContent.ArCsidOffHeader%></h4>
<button class="abc bcd cde" title="Button" id="buttondiv"><span>Button</span></button> //Want to hide this button
</div>
</div>
<% } %>
</asp:Content>
Now in the cs file i want to hide the button with id "buttondiv", how can i do that
In my cs file, i try this 2 things but it doesnt work
Control myDiv = (Control)FindControl("buttondiv");
myDiv.Visible = false;
Or
foreach (Control c in contentid.Controls)
{
if (c.ID == "buttondiv")
{
c.Visible = false;
}
}
Can anyone let me know
In order to be used as a server-side control, the button would need to be a server-side control. Add runat="server":
<button class="abc bcd cde" title="Button" id="buttondiv" runat="server">
Then (unless you've broken the designer somehow, it's been a while since I've used Web Forms) you should have an HtmlControl object in your class that you can set without the need to "find" the control:
this.buttondiv.Visible = false;
Kindly keep this in css file.
#buttondiv{
display:none;
}
Or apply style inline like below:
<button class="abc bcd cde" title="Button" id="buttondiv" style="display:none"><span>Button</span></button>

Selecting jQuery First Child without a specific class

I have a page with nested divs being used as Js/Jq tabs. When you click on a parent tab, it fires the click event of the first child underneath the parent.
$('#topRow .pricing').click(function () {
$('#secondRow .pricing').css('display', 'block');
$('#secondRow .pricing div.tab:first-child').trigger('click');
});
This functionality works great as is. However, we're adding functionality to effectively "lock" tabs by adding a "locked" class dynamically via c#/linq and then on window.ready we unbind all the tabs with the "locked" class and color them grey to indicate that they are disabled.
I'm trying to modify the last line of the jQuery code above to click the first child that DOESN'T have the "locked" class.
$('#secondRow .pricing div.tab:first-child').trigger('click');
Translating that into plainspeak, it's saying "In the Second Row, fire the click event of the first child tab in the 'pricing' group". I'd like it to say "In the Second Row, fire the click event of the first child tab in the 'pricing' group that DOES NOT have the class 'locked'".
I've tried using:
$('#secondRow .pricing div.tab:not(.locked):first-child').trigger('click');
Which seems the correct way to do this, but it still looks at the first child and just doesn't fire the trigger('click'). Am I missing something?
Here is the html:
<div id="topRow">
<div class="pricing tab" runat="server" id="pricingTop">
<div class="tabLeft">
<div class="tabMain">
Pricing
</div>
</div>
</div>
</div>
<div id="secondRow">
<div id="pricingTabGroup" runat="server" class="pricing tabGroup" style="display:none">
<div id="pricingProductA" runat="server" class="tab locked pricingProductA">
<div class="tabLeft">
<div class="tabMain">
ProductA
</div>
</div>
</div>
<div id="pricingProductB" runat="server" class="tab pricingProductB">
<div class="tabLeft">
<div class="tabMain">
ProductB
</div>
</div>
</div>
</div>
</div>
The "locked" class is added through C#:
protected void Page_Load(object sender, EventArgs e)
{
bool ProductA = //some linq query
if (!ProductA)
{
LockTab(pricingProductA);
}
protected void LockTab(HtmlGenericControl tab)
{
//Adds the "locked" class
tab.Attributes.Add("class", "locked");
}
}
Try
$('#secondRow .pricing div.tab').not('.locked').children().first().trigger('click');
Your selector looks fine though. Usually a good idea to minimize your selector complexity.
Also remember that every time you do a selector jQuery traverses the dom, so its best to save returned elements for a given selector as a variable(for performance) eg:
var $tab_containers = $('#secondRow .pricing div.tab');
And then use it multiple times like
$tab_containers.not('.locked').children().first().trigger('click');

making div/htmlgeneric control visible using asp.net

I have a user control with a div like this:
<div runat="server" id="pnlShippingMethods" class="checkoutstep">
<div class="steptitle">
<%=GetLocaleResourceString("CheckoutOnePage.ShippingMethods.Title")%>
<div style="float: right;">
</div>
Date from checkout page one for ship method update panel is <%= DateTime.Now.ToString() %>
</div>
<asp:Panel runat="server" ID="pnlShippingMethodsContent" class="stepcontent">
<nopCommerce:CheckoutShippingMethod ID="ctrlCheckoutShippingMethod" runat="server"
OnePageCheckout="true" />
</asp:Panel>
</div>
I am making in visible = false on page load where this control is placed. Then from another control on the same page I am trying to make it visible like this:
HtmlGenericControl pnlShippingMethods = this.Parent.Parent.Parent.Parent.Parent.FindControl("pnlShippingMethods") as HtmlGenericControl;
pnlShippingMethods.Visible = true;
I am able to make visible/invisible user control CheckoutShippingMethod from other user control but not the div. Please suggest how to make it visible
You can use public method instead of it.
1) Make public method/Property in the custom control where you want to show/hide
panel.
public void ShowPanel(bool isVisible)
{
this.pnlShippingMethods.Visible = isVisible;
}
2) Call this from the other control to show hide panel.
yourCustomrControlObject.ShowPanel(true);

How to lazy load content on JQuery tabs that doesn't pertain to any of the tab content(ie. login section or registration section)

I am lazy loading 3 tabs using Query tabs in an asp.net mvc web app. I have a Login section(username and password) that I would like to display where the tab content usually shows. I would like this Login section to only load when the user clicks the link at the top of the page. So, I need it lazy loaded too. How would I do that, I can't seem to figure it out. Below is my current tab code. I appreciate your help!
<script type="text/javascript">
$(document).ready(function()
{
$("#tabContainer").tabs();
});
</script>
<div id="menu" style=" background-color:White; width:950px; height:400px; float:left;">
<div id="tabContainer">
<ul>
<li>Home</li>
<li>Products</li>
<li>Contact Us</li>
</ul>
</div>
</div>
ok, you need to add the select: event onto your tabs code. here's a quick example:
<div id="menu" style=" background-color:White; width:950px; height:400px; float:left;">
<div id="tabContainer">
<ul>
<li>Home</li>
<li>Products</li>
<li>Contact Us</li>
</ul>
<div id="tab0"></div>
<div id="tab1"></div>
<div id="tab2"></div>
</div>
</div>
<script>
$(function() {
var $tabs = $("#tabContainer").tabs({
select: function(e, ui) {
var thistab = ui;
runMethod(thistab.index);
}
});
});
function runMethod(thistab) {
selectedtab = thistab;
switch (thistab) {
case 0:
getTab0Data();
break;
case 1:
getTab1Data();
break;
case 2:
getTab2Data();
break;
}
}
function getTab0Data(){
alert("you clicked Tab 0");
}
function getTab1Data(){
alert("you clicked Tab 1");
}
function getTab2Data(){
alert("you clicked Tab 2");
}
</script>
[EDIT] - i've updated the example so that it runs. both jquery base lib and jquery UI need to be referenced in the page. I also added a jsfiddle to demo it in action: http://jsfiddle.net/jimibt/k7ZN6/
basically, the getTab*n*Data() function(s) run an ajax request that populates the appropriate div (i.e. tab0, tab1, tab2 etc) as per the amended structure above.
for jquery ajax, see:
http://api.jquery.com/jQuery.ajax/
hope this helps

Categories