Event Modifier on Quasar QSelect Remove Event - events

I want to remove an option from selection conditionally.. I tried to use #remove event but I couldn't stop remove event before my check... I want to do something below;
<q-select #remove.stop="isItRemovable"></q-select>
.
.
.
methods: {
isItRemovable(option) {
if (option.value.name === 'yes removable') {
remove
} else {
show not removable warning
}
}
}
how can i do this? than you.

I encountered the same problem and figured out a dirty solution
function onRemove(details) {
setTimeout(()=>{
tags.value.splice(details.index, 0, details.value as never);
}, 1) // yes this is very dirty, but it seems to me there is no better way with current Quasar API
}
Where tags is your ref used as v-model and this function is used as event callback: #remove="onRemove".
This will prevent any item removal, but of course you can add any conditions. Side effect: element blinks for a millisecond.

Related

Cypress Click if item exist

I need a way to easily trigger a click() event only if an element exist on page.
the fact that the element (confirm modal dialog) itself exist is not an issue for my test, but this can stop next steps. so I want to click OK only if the dialog is shown.
I tried something like this, but it didn't work:
cy.get('body').find("button[data-cy=sometag]").then(items => {
if(items.length) {
cy.get('button[data-cy=sometag]').click();
}
});
If you want to test that the modal exists but don't want to fail the test if it doesn't, use a jQuery selector.
const found = Cypress.$('button[data-cy=sometag]').length
Modals are likely to animate on opening, so you you will need to repeat the check a few times, which you can do in a function
function clearModal(selector, timeout = 1000, attempts = 0)
if (attempts > (timeout / 100)) {
return; // modal never opened
}
if (!Cypress.$(selector).length) { // not there yet, try again
cy.wait(100)
clearModal(selector, timeout, ++attempts)
else {
Cypress.$(selector).click() // modal is up, now close it
}
}
clearModal('button[data-cy=sometag]')
If you use the find like this cy.get('body').find("button[data-cy=sometag]") this will fail always whenever the element is not present. Instead you can use the find command inside the If condition and check its length.
cy.get('body').then($body => {
if ($body.find("button[data-cy=sometag]").length > 0) {
cy.get('button[data-cy=sometag]').click();
} else {
//Do something
}
})
Instead of body, you can also use the parent element of the element in question, which you know for sure is visible and present on the page every time.

FIre event on toggle of v-show

I am using Laravel with Vuejs. i want to fire an event on component show or hide. how to achieve this?
<album-images v-show ="!gallery"
:album = "album"
:image-arr = "imageArr"></album-images>
You can use a watcher:
watch: {
gallery: {
handler: value => {
this.$emit('gallery-toggled', value)
}
}
}
or a computed:
computed: {
toggle () {
this.$emit('gallery-toggled', this.gallery)
}
}
If you want to do something after the view has updated (i.e the component is actually visible or hidden), you may have to wrap the $emit in nextTick(), see Vue.nextTick( [callback, context] ).
It depends on the exact order of updating the watch or computed, but if you are getting unexpected results in the receiver of the event, this is an option to try.
See the discussion here.
this.$nextTick(function() {
this.$emit('galleryVisible', this.gallery)
});

How to detect when a marker is found in AR.js

I'm trying to detect when a marker if found/lost in ar.js, while using a-frame.
From what I see in the source code, when the marker is found, a 'getMarker' event should be fired, moreover artoolkit seems to dispatch a markerFound event.
I tried to listen to those events on the <a-scene>, or on the <a-marker>, but it seems I'm either mistaken, or i need to get deeper to the arController, or arToolkit objects.
When i log the scene, or the marker, i only get references to the attributes, which don't seem to have the above objects attached.(like marker.arController, or marker.getAttribute('artoolkitmarker').arController)
Did anybody tried this and have any tips how to do this ?
PR303 introduces events when a marker is found and lost
markerFound
markerLost
You can use them by simply adding an event listener:
anchorRef.addEventListener("markerFound", (e)=>{ // your code here}
with a simple setup like this:
<a-marker id="anchor">
<a-entity>
</a-marker>
example here.
Please note, that as of sep 18', you need to use the dev branch to use the above.
ORIGINAL ANWSER - in case you want to do it manually
Detecting if the marker is found is possible by checking if the marker is visible when needed (other event, or on tick): if(document.querySelector("a-marker").object3D.visible == true)
For example:
init: function() {
this.marker = document.querySelector("a-marker")
this.markerVisible = false
},
tick: function() {
if (!this.marker) return
if (this.marker.object3D.visible) {
if (!this.markerVisible) {
// marker detected
this.markerVisible = true
}
} else {
if (this.markerVisbile) {
// lost sight of the marker
this.markerVisible = false
}
}
}
As adrian li noted, it doesn't work with a-marker-camera, only with a-markers
I went with a dirty hack diving into the internals, bear in mind that what I've provided might not suffice because the event get's called every time the marker is found, sadly I couldn't find an event to hook into for markers being lost.
const arController = document.querySelector("a-scene").systems.arjs._arSession.arContext.arController;
arController.addEventListener("getMarker", (evt) => {
const markerType = evt.data.type;
const patternType = 0;
//console.log("onMarkerFound!!");
if (markerType == patternType) {
//console.log("onMarkerFound out pattern!!");
//Do stuff...
}
});

Prototype.js event.target.id for child elements

I want to hide a div when clicking somewhere else in the page. For this, I have:
$(document.body).observe('click', function(e){
if(e.target.id != 'myDiv') {
$('myDiv').hide();
}
});
Works fine, the only problem is that inside this div I have other elements, and clicking them also closes #myDiv. I want it so that clicking anything inside this div won't trigger the hiding. After searching around, I found the answer here on how to do this with jQuery: https://stackoverflow.com/a/12222263/548524. However, I can't seem to get this working in Prototype, and obviously has() is not valid here.
Any help is much appreciated!
document.observe('click', function(event) {
if (!event.findElement('#myDiv')) {
$('myDiv').hide();
}
});
You don't need $(document.body) - there is already document-wide observe
There is a method to find element from event
Use the 'up' function:
$(document.body).observe('click', function(e){
if(e.target.id != 'myDiv' && !$(e.target.id).up('#myDiv')) {
$('myDiv').hide();
}
});

Slickgrid - One-click checkboxes?

When I create a checkbox column (through use of formatters/editors) in Slickgrid, I've noticed that it takes two clicks to interact with it (one to focus the cell, and one to interact with the checkbox). (Which makes perfect sense)
However, I've noticed that I am able to interact with the checkbox selectors plugin (for selecting multiple rows) with one click. Is there any way I can make ALL of my checkboxes behave this way?
For futher readers I solved this problem by modifing the grid data itself on click event. Setting boolean value to opposite and then the formatter will display clicked or unclicked checkbox.
grid.onClick.subscribe (function (e, args)
{
if ($(e.target).is(':checkbox') && options['editable'])
{
var column = args.grid.getColumns()[args.cell];
if (column['editable'] == false || column['autoEdit'] == false)
return;
data[args.row][column.field] = !data[args.row][column.field];
}
});
function CheckboxFormatter (row, cell, value, columnDef, dataContext)
{
if (value)
return '<input type="checkbox" name="" value="'+ value +'" checked />';
else
return '<input type="checkbox" name="" value="' + value + '" />';
}
Hope it helps.
The way I have done it is pretty straight forward.
First step is you have to disable the editor handler for your checkbox.
In my project it looks something like this. I have a slickgridhelper.js to register plugins and work with them.
function attachPluginsToColumns(columns) {
$.each(columns, function (index, column) {
if (column.mandatory) {
column.validator = requiredFieldValidator;
}
if (column.editable) {
if (column.type == "text" && column.autocomplete) {
column.editor = Slick.Editors.Auto;
}
else if (column.type == "checkbox") {
//Editor has been diasbled.
//column.editor = Slick.Editors.Checkbox;
column.formatter = Slick.Formatters.Checkmark;
}
}
});
Next step is to register an onClick event handler in your custom js page which you are developing.
grid.onClick.subscribe(function (e, args) {
var row = args.grid.getData().getItems()[args.row];
var column = args.grid.getColumns()[args.cell];
if (column.editable && column.type == "checkbox") {
row[column.field] = !row[column.field];
refreshGrid(grid);
}
});
Now a single click is suffice to change the value of your checkbox and persist it.
Register a handler for the "onClick" event and make the changes to the data there.
See http://mleibman.github.com/SlickGrid/examples/example7-events.html
grid.onClick.subscribe(function(e, args) {
var checkbox = $(e.target);
// do stuff
});
The only way I found solving it is by editing the slick.checkboxselectcolumn.js plugin. I liked the subscribe method, but it haven't attached to me any listener to the radio buttons.
So what I did is to edit the functions handleClick(e, args) & handleHeaderClick(e, args).
I added function calls, and in my js file I just did what I wanted with it.
function handleClick(e, args) {
if (_grid.getColumns()[args.cell].id === _options.columnId && $(e.target).is(":checkbox")) {
......
//my custom line
callCustonCheckboxListener();
......
}
}
function handleHeaderClick(e, args) {
if (args.column.id == _options.columnId && $(e.target).is(":checkbox")) {
...
var isETargetChecked = $(e.target).is(":checked");
if (isETargetChecked) {
...
callCustonHeaderToggler(isETargetChecked);
} else {
...
callCustonHeaderToggler(isETargetChecked);
}
...
}
}
Code
pastebin.com/22snHdrw
Search for my username in the comments
I used the onBeforeEditCell event to achieve this for my boolean field 'can_transmit'
Basically capture an edit cell click on the column you want, make the change yourself, then return false to stop the cell edit event.
grid.onBeforeEditCell.subscribe(function(row, cell) {
if (grid.getColumns()[cell.cell].id == 'can_transmit') {
if (data[cell.row].can_transmit) {
data[cell.row].can_transmit = false;
}
else {
data[cell.row].can_transmit = true;
}
grid.updateRow(cell.row);
grid.invalidate();
return false;
}
This works for me. However, if you're using the DataView feature (e.g. filtering), there's additional work to update the dataview with this change. I haven't figured out how to do that yet...
I managed to get a single click editor working rather hackishly with DataView by calling
setTimeout(function(){ $("theCheckBox").click(); },0);
in my CheckBoxCellEditor function, and calling Slick.GlobalEditorLock.commitCurrentEdit(); when the CheckBoxCellEditor created checkbox is clicked (by that setTimeout).
The problem is that the CheckBoxCellFormatter checkbox is clicked, then that event spawns the CheckBoxCellEditor code, which replaces the checkbox with a new one. If you simply call jquery's .click() on that selector, you'll fire the CheckBoxCellEditor event again due because slickgrid hasn't unbound the handler that got you there in the first place. The setTimeout fires the click after that handler is removed (I was worried about timing issues, but I was unable to produce any in any browser).
Sorry I couldn't provide any example code, the code I have is to implementation specific to be useful as a general solution.

Resources