Evaluating an expression in AngularJS ng-show directive - javascript

Background: As part of a project I'm working on, Users (referred to as "artists" in the case below) can optionally select one or more from a series of Roles: Manager, Producer, Agent, and so forth. Consequently, I need to show or hide certain parts of page depending on which Role(s) the User has selected.
The example: I've tried using the following to conditionally show a div when the User has selected "Manager" as one of his/her Roles (and have it hidden when "Manager" isn't selected), but with no luck. What should I be using in the ng-show directive instead?
<div class="manager_section" ng-show="data.artist.roles.name == 'Manager'">Sample Text Here</div>
Please note: the div appears just fine with no ng-show/ng-hide directive applied, so I'm not looking for a CSS answer or anything; I'm simply looking for the conditional aspect provided by ng-show/ng-hide. And I know the data for the Roles is being pulled to the page, because when I ran the following on the page to test it, the names of each of the Roles the User had selected were accurately displayed:
<div ng-repeat="role in data.artist.roles">{{ role.name }}</div>

You can use controller method if you need to run arbitrary JavaScript code.
For example:
<div class="manager_section" ng-show="isAuthorized('Manager')">Sample Text Here</div>
angular.module('myApp', [])
.controller('AppCtrl',function(){
$scope.isAuthorized = function(role){
for(var i=0;i<$scope.data.artist.roles.length;i++){
if($scope.data.artist.roles[i].name === role) return true;
}
return false;
}
};

Related

How to two-way bind a checkbox using Angular?

I currently have an accordion with a bunch of options in the form of checkboxes. The user can select the checkboxes as expected however, I want to already have some of those checkboxes checked depending on certain conditions. The issue is sometimes that is determined after the page has loaded. Below are simplified examples to demonstrate my code (my code is for work and would not be able to share due to confidentiality issues).
My HTML looks like this:
<div class="row">
<div "ngFor="let value of filteredPeople" >
<div>
<input type="checkbox" (click)="selectPeople(value)" [checked]="checkedPeople.get(value)">
{{ value }}
</div>
</div>
</div
My Javascript:
public checkPeople() {
this.selectedPeople.forEach(element => {
this.checkedPeople.set(element, true);
});
}
To explain some variables and methods:
Variables:
filterPeople - a string array of all possible people
checkedPeople - a map with a KVP of string (the people) and boolean (whether or not their checkbox is checked)
selectedPeople - a string array of people whose checkboxes I want already checked
Methods:
selectPeople - checks the corresponding checkbox when user clicks on it
checkPeople - a method called when I want the specific checkboxes checked (these specific checkboxes change based on other factors so I cannot hard code it)
For some reason my checkPeople method does not seem to select the expected checkboxes, I am not sure why but I have a feeling it is to do with the fact that I have used "[checked]" in the HTML and that it should be something else. Can someone clarify the issue for me and help me identify a fix? (Note: as the title suggests, I am using Angular)
Edit:
I have just debugged my code and added breakpoints, the checkedPeople map has the correct mapping of people to true for each of the elements in selectedPeople which shows that the checkPeople method is working as expected. Therefore the issue must be with the [checked] attribute if I'm not mistaken. I cannot see why it wouldn't work though.
You should use [ngModel]="checkedPeople.get(value)"
instead of [checked]="checkedPeople.get(value)"
to initialize the checkbox and
(change)="checkUncheckPeople(value, $event)"
to update the value when you check or uncheck it, where
checkUncheckPeople(value, e) {
this.checkedPeople.set(value, e.target.value);
}
So, in conclusion, your HTML input element will be:
<input
type="checkbox"
[ngModel]="checkedPeople.get(value)"
(change)="checkUncheckPeople(value, $event)"
/>
If you choose to use an object instead of a map then you can also directly use
[(ngModel)]="checkedPeople[value]"
to two-way bind the variable

Django Modelmultiplechoicefield Checkboxselectmultiple Problem Getting Selected Checkbox

I have been working all day to try and get the selected values on one set of checkboxes on my Django form and copy the selected ones only to an identical checkbox on my form. If a user clicks on a checkbox in form.author defined below, I want the same identical checkbox to automatically be checked on form.favorite_author defined below.
I've tried a JQuery approach as documented here...Copy Selected Checkbox Value From One Checkbox To Another Immediately Using JQUERY but no luck so far. I've recently begun exploring an avenue with the Modelmultiplechoicefield and the checkboxselectmultiple parameters within the form itself. From what I can tell, when I am using JQuery and trying to check a box on the form, the value is coming back as undefined which is most likely why it is not propagating the checkbox selection to the other checkbox.
Here is my form....
class ManagerUpdateNewAssociateForm(forms.ModelForm):
class Meta:
model = Library
self.fields['author'] = forms.ModelMultipleChoiceField(
widget=forms.CheckboxSelectMultiple(),
queryset=Books.objects.all()
self.fields['favorite_author'] = forms.ModelMultipleChoiceField(
widget=forms.CheckboxSelectMultiple(),
queryset=Books.objects.all()
My HTML...
<div class="spacer83">
{{ form.author }}
</div>
<div class="spacer83">
{{ form.favorite_author }}
</div>
When I tried to trace JQuery, it told me the checkbox selections are undefined. I did read a bit about how Modelmultiplechoicefield, since it uses a queryset it doesn't show the selections, but I can't figure out how to get it to.
Thanks in advance for any thoughts.
In combination with the other issue included in this one, I went back to the JQuery route and explored further. From what I can tell, I was not able to use the class for the input because of the way the HTML for Django forms is generated in this use case. I ultimately was able to leverage the input name and then used the code below to interrogate the checkboxes accordingly:
$(document).ready(function() {
$("[name=author]").change(function() {
let selectedValA = $(this).val();
let isAChecked = $(this).prop("checked");
$(`[name=favorite_author][value="${selectedValA}"]`).prop("checked", isAChecked);
});
});
});

How to capture the value for one of the custom ticket fields in zendesk on the new request page?

In Zendesk's help center, I have a new request page set up which allows the end-user to submit a request.
For one of the questions, there is a dropdown which asks the client to establish whether they are using the basic or enterprise version.
If basic, I would like to display some text, perhaps a modal that has messaging around the prioritization for our customers.
However looking at the code, it isn't apparent how to capture the value from the dropdown to display the messaging accordingly.
So far I didn't see a clear way to accomplish this, I've been looking at the documentation here https://developer.zendesk.com/apps/docs/help-center-templates/new_request_page#content
This is the code that's set up on the New Request Page template.
{{breadcrumbs}}
<div class="clearfix">
<section class="main-column">
<h1>{{t 'submit_a_request'}}{{#if parent}}
<span class="follow-up-hint">
{{follow_up}}
</span>
{{/if}}</h1>
<div class="form">
{{request_form}}
</div>
</section>
{{chat}}
You will want to grab the selected value with something like this (using jQuery for simplicity):
$('#request_custom_fields_' + custom_field_id).attr('value');
You can inspect the DOM to see the id. The resulting value will be the tag name you have assigned to the selected value of the custom field.
You can grab it on change and react to it with something like:
$('#request_custom_fields_' + custom_field_id).change(function(){
if ($(this).attr('value') == 'my_cool_tag_value') {
//Do your stuff
}
});

Select field populated with multiple entries after one checkbox change

I have something in my mind, but I have no idea how to get it done, so I hope I can get some advise here.
I'm working on an activity registration app (using Laravel), where every activity will be registered. Very important is that we need to record who was invited and who actually attended. I already have this part running. My issue is more on the practical side.
I use jQuery Select2 for the multiple select fields for invitees and attendees. Imagine now that there's a group of users that need to be invited or attend virtually all activities, while the invitation or attendance of others depends on the type of activity. Using Select2, I can only select users one at a time and that sucks if you need to do that for, say, 50 users for virtually every activity.
What is the best way to have a "group" that can be selected, which selection fills in all the names of those in the group in the select field? Or is there a better way to get this done?
I'm seeing something in my head, where there are checkboxes next to the select field, representing the groups. When you tick a checkbox of a group, the select field is populated with all users who are part of that group.
I have no idea ow this can be done. I looked around and every search brings up select boxes populating select boxes. None handle checkboxes.
Any advise on how to get this done?
My PHP/MySql is intermediate, Javascript/Ajax is very basic.
One strategy would be to build a control (checkbox element) that will set or toggle the selection of your group of users whenever it's clicked. Say we have the following markup:
<select class="my-big-group-select" multiple="multiple">
<!-- assorted options here -->
</select>
<label>
<input type="checkbox" class="toggle-default-group" />
Use my default big group of users
</label>
The Select2 API allows you programmatic control over the component it generates.
You can read more about it here: https://select2.github.io/examples.html#programmatic
Here's one way to leverage this knowledge using jQuery with Select2:
<script>
var groupSelect = $('.my-big-group-select').select2();
var groupToggle = $('.toggle-default-group');
var myBigGroup = ["Aaron", "Beth", "Cindy"]; // assorted option values
groupToggle.on("click", function() {
if ($(this).is(':checked')) {
groupSelect.val(myBigGroup).trigger('change');
} else {
var currentlySelected = groupSelect.val();
if (currentlySelected) {
var filteredSelections = currentlySelected.filter(function(key) {
return myBigGroup.indexOf(key) < 0;
});
groupSelect.val(filteredSelections).trigger('change');
}
}
});
</script>
Here's a CodePen that shows it all in action: http://codepen.io/anon/pen/qNQKOd
Of course you can build on this to make additional enhancements (the ability to select multiple groups, for example).
As an alternative, you may consider other code libraries like Bootstrap Multiselect: https://davidstutz.github.io/bootstrap-multiselect/
Hope this points you in the right direction!

How to make Collapsible comment box like Stackoverflow

I am building a site and I have a list of status updates and I want to allow the users to write comments for each of of the items in the list
However I am trying to implement a UI similar to the way stack overflow works
specifically the collapsible comment form / list where a user clicks on add comment on the specific status update in the list, and below that item in the list the comment entry form shows up along with the specific comments already posted.
How do I accomplish this using Jquery?
Note: looking also for the markup example another words a working sample. Thanks
And yes if you could show Async postback that would be nice too
To load the content you can just hook up a click event to populate a div using the load method.
For example in the view you could have something like:-
<%= Html.ActionLink("Comments", "CommentList", "Questions", new { Id = this.ViewData.Model.Id }, new { id = "commentLink" })%>
<div id="commentContainer" style="display:none;">
Loading...
</div>
while the javascript to hook everything up would be:-
$(function() {
$("#commentLink").click(function() {
$("#commentContainer").toggle();
if ($("#commentContainer").is(":visible")) {
$("#commentContainer").load($(this).attr("href"));
} else {
$("#commentContainer").html("Loading..."); //Or just leave it as is...
}
return false; //Prevent default action
});
});
The quick approach (for just showing / hiding the comment area) would resemble something like this:
$(function(){
$('#id_of_element_to_use_for_click').click(function(){
$('#id_of_comment_area').slideToggle();
});
});
The jQuery site will provide you with doco on different approaches such as fades, slides or other combined animations.
Your "Comment Area" I've used in the example here would likely be a <div> tag that contains your existing comments, plus whatever textarea or text input box you wanted users to type their answers into.
Do you need to do an asynchronous postback?

Categories

Resources