Semantic UI dropdown value getting retained, when the table row is deleted - javascript

A table is rendered with rows based on the values inside the array 'results'. There is a dropdown present in each of the row, which is populated via an array 'statuses'.
<div id="app">
<table>
<tr v-for="(row,index) of results">
<td>{{index}}</td>
<td>{{row.name}}</td>
<td>
<div :id="row.id"
class="ui selection dropdown status_dropdown">
<i class="dropdown icon"></i>
<div class="text">{{row.status}}</div>
<div class="menu">
<div class="item" v-for="status of statuses"
:data-index="index">
{{status.status}}
</div>
</div>
</div>
</td>
</tr>
</table>
</div>
Following is change dropdown function, which basically removes the row if the selected text in dropdown is "Delete":
$('.status_dropdown').dropdown({
onChange: function(value, text, $choice) {
let temp_index = $($choice).attr("data-index");
if(text === "Delete"){
vm.results.splice(temp_index,1);
}
}
});
Here's a codepen with complete code: https://codepen.io/anon/pen/KxzZOB
Now, if the status is changed to "Delete", although the row gets removed, the value of dropdown "Delete" is getting retained on that row.
To reproduce in the codepen sample, change the first row's status (index 0) to "Delete". You'll see that status for "Doe" appears as "Delete".
Also, if any of the dropdown value is changed. And some other row's dropdown value is changed, the previous row for which the status was changed retains the value.
To reproduce in the codepen sample, reload the page. Now, change the status for third row (index 2) to "Active". Now delete the second row (index 1) by selecting "Delete". You'll see last row retaining the value "Active".
Can someone help me out with this issue?

To resolve this issue, you can define the key. see below:
<div id="app">
<table>
<tr v-for="(row,index) of results">
<td>{{index}}</td>
<td>{{row.name}}</td>
<td>
<div :id="row.id"
:key="row.id"
class="ui selection dropdown status_dropdown">
<i class="dropdown icon"></i>
<div class="text">{{row.status}}</div>
<div class="menu">
<div class="item" v-for="status of statuses"
:data-index="index">
{{status.status}}
</div>
</div>
</div>
</td>
</tr>
</table>
</div>
Defining the key should maintain the dom item instance while it moves within the table.

Related

Angular 6: onChage mat-slide-toggle conditional validation to select only one option from array of objects

I have a list of the mat-slide-toggle. At a time only one slider will remain enabled and other slider will remain disabled.
Now while clicking on that enabled slider it's value will be changed and simultaneously other list of slider will be get enabled for selection and once the one slider will be get selected then other will be get disabled.
So, in short from the whole array only one mat-slide-toggle should be selected and other will be disabled simultaneously.
For that I have make the code as below.
<form [formGroup]="selectionForm">
<div class="row">
<div formArrayName="selectOption">
<div *ngFor="let select of selectionForm['controls'].selectOption['controls']; let i=index">
<div [formGroupName]="i">
<div formArrayName="selectionList">
<div *ngFor="let obj of select.controls['selectList'].controls; let j = index">
<div [formGroupName]="j">
<mat-slide-toggle formControlName="isSelected"" (change)="changeSelection($event)" disabled="slidValue || obj.isSelected === false"> Is selected? </mat-slide-toggle>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</form>
In TS code:
public slidValue;
changeSelection(event) {
this.slidValue = false
}
Sample JSON Response
StackBlitz demo.
Eg: On load of the page:
Now when change the slide toggle all other options value not getting change from false to true for selection.

How to select the clicked element in a ng for and add class only to the selected element?

I have a list and my last column should be like apples "more options icon", so that a dropdown pops up with additional options.
<tr *ngFor="let foo of bars">
<td>{{foo.id}}</td>
<td>{{foo.name}}</td>
<td class="more-options-menu">
<i class="icon i-menu" (click)="toggleOptionsMenu()"></i>
<div id="more-options-{{foo.id}}" [className]="!toggleOptions ? 'more-options-menu-content' : 'more-options-menu-content show-menu'">
Link 1
Link 2
Link 3
</div>
</td>
</tr>
The problem i am having is, that if i click one of the items in the list, the css class "show-menu" is added to all of the listitems, so that the menu is shown on all items and not just the one I clicked. How can I add the class only to the selected item?
I tried using the id "more-options-xx", but I also cant figure out how.
I would suggest that you keep track of the selected id as a separate property on your component. For example:
selectedId = null;
toggleOptionsMenu(id) {
this.selectedId = id;
}
In your template:
<i class="icon i-menu" (click)="toggleOptionsMenu(foo.id)"></i>
<div id="more-options-{{foo.id}}" class="more-options-menu-content"
[class.show-more]="foo.id === selectedId">

Semantic ui dropdown, prevent auto select with input element

I added an option to the dropdown that allows user to add item if it doesn't exist.
For that matter, I added an input field to the dropdown but when the user enters something, the dropdown tries to match the entered text with items that are already in the list.
I find it quite annoying in that specific case. I have noticed in the docs that input elements are bound to the search function. Nevertheless, I couldn't find how to disable this behaviour.
Here's the HTML:
<div class="ui fluid selection dropdown playlist">
<input name="playlist" type="hidden">
<i class="dropdown icon"></i>
<div class="default text">playlist</div>
<div class="menu">
<div class="item create" data-value="0">
<span class="create-placeholder">+ new playlist</span>
<div class="ui action input add-playlist">
<input placeholder="new playlist">
<button class="ui button">Add</button>
</div>
</div>
<div class="item" data-value="1">foo</div>
<div class="item" data-value="2">bar</div>
<div class="item" data-value="3">baz</div>
</div>
</div>
The .add-playlist div and its content are not shown but I'm willing to spare you with the CSS here.
And the js:
$dropdown = $('.ui.dropdown');
$dropdown.dropdown({
action: (text, val) => {
if (val == 0) { // eslint-disable-line
$('.create-placeholder').hide(100);
$('.add-playlist').css('display', 'inline-flex');
$('.add-playlist input, .add-playlist button').show(200);
}
else $dropdown.dropdown('set selected', val).dropdown('hide');
},
onHide: () => {
// do that after dropdown has been hidden
setTimeout(() => {
$('.add-playlist, .add-playlist input, .add-playlist button').hide();
$('.create-placeholder').show();
}, 400);
}
});
I've set up a fiddle to have a clear exemple. Just type "foo" and you'll see what I mean in case it's not crystal clear.
To allow user to add new items just add allowAdditions: True To dropdown options, for more informtions see semantic-ui dropdown settings
Example:
$('dropdownSelector').dropdown({
allowAdditions: True
}).dropdown();

Clicking a checkbox with protractor?

HTML code
<div class="check-box-panel">
<!--
ngRepeat: employee in employees
-->
<div class="ng-scope" ng-repeat="employee in employees">
<div class="action-checkbox ng-binding">
<input id="John" type="checkbox" ng-click="toggleSelection(employee.name)"
ng-checked="selection.indexOf(employee.name) > -1" value="John"></input>
<label for="John">
::before
</label>
<!--
John
end ngRepeat: employee in employees
-->
<div class="ng-scope" ng-repeat="employee in employees">
<div class="action-checkbox ng-binding">
<input id="Jessie" type="checkbox" ng-click="toggleSelection(employee.name)"
ng-checked="selection.indexOf(employee.name) > -1" value="Jessie"></input>
<label for="Jessie"></label>
I tried using jQuery
element(by.repeater('employee in employees')).element(by.id('Jessie')).click();
also,I tried using css
element(by.repeater('employee in employees')).$('[value="Jessie"]').click();
But it didn't do the job. Any other way I can click on the particular Checkbox?
Alright I had a very similar issue where I couldn't click the checkbox. It turned out I had to click the checkbox label. However if you want to do any checks on if the checkbox is selected then you have to check the actual checkbox. I ended up making two variables, one for the label and one for the actual checkbox.
JessieChkbxLabel = element(by.css("label[for='Jessie']"));
JohnChkbxLabel = element(by.css("label[for='John']"));
//Click the Jessie checkbox
JessieChkbxLabel.click();
//Click the John checkbox
JohnChkbxLabel.click();
You should just need to use element(by.id('Jessie')) to grab your object. The issue you might be having is that click() returns a promise, so you need to handle that with a .then. So something along the lines of:
element(by.id('Jessie')).click().then(function(value) {
// fulfillment
}, function(reason) {
// rejection
});
Aside from checking the id directly, you can also filter the desired element checking the employee name:
var employee = element.all(by.repeater('employee in employees')).filter(function (elm) {
return elm.evaluate("employee.name").then(function (name) {
return name === "Jessie";
});
}).first();
employee.element(by.css("input[type=checkbox]")).click();

how to show/hide div based on drop down selection using angular?

i want to show and hide a div based on selection from the drop down , here is my code, this is my html code for dropdown which fetches the values from the "selectItemsFilterCriteria" json structure
<select ng-model="appointment" ng-change="changeme()" ng-options="item.name for item in selectItemsFilterCriteria">
<option ng-option value="" >Filter Criteria</option>
</select>
this is my changeme() function created inside a controller
$scope.changeme = function() {
$scope.appointment = $scope.items[0];
}
this is code for my div that is to be show or hide , right now my code is working on selection of first option from drop down it is showing me the div but the problem is that its not hiding that div on the selection of any other option from the dropdown list, kindly tell me where i m doing wrong??
<div class="mycontainer" ng-show=appointment >
<div class="left-nav">
<accordion close-others="true">
<accordion-group ng-repeat="item in pagedItems[currentPage] |filter:{name:item.name}| orderBy:sortingOrder:reverse">
<accordion-heading>
<table>
<tr class="odd" ng-click="showDataDetail=!showDataDetail" style="cursor: pointer">
<td><p class="lead-name">{{item.name}}</p>
<p class="call-up-icon">{{item.phoneNo}} </p>
<p>Lead Date : 07/02/2015</p></td>
<td><p></p>
<p class="blue-txt">{{item.trade}}</p>
<p class="fl cstm-wdth">GNU09</p>
<p class="fl">{{item.time}}</p>
<div class="cb"></div>
</td>
<td><p>Today</p>
<p>C#SQL</p>
<p class="blue-remark-icon"></p></td>
</tr>
</table>
</accordion-heading>
<div>{{item.data}}</div>
</accordion-group>
</accordion>
</div>
</div>
items array:
$scope.selectItemsFilterCriteria = [
{id:1 , name:"Appointments Scheduled"},
{id:2 , name:"fresh leads"}
];
Basically the problem is with your ng-change function call,
$scope.changeme = function() {
$scope.appointment = $scope.items[0];
}
You are setting appointment to first value of items array. Hence whenever you change the options, the function sets it back to first option , in turn the div is shown.
Please remove the ng-change function and try.
Remove the $scope.changeme() function. It is not necessary.
Since you are using ng-model on select whatever option you select will get assigned to the ng-model i.e appointment in your case.
Here is the plunkr example

Categories

Resources