VueJs - How can i know when the scroll bar of DIV reach its bottom - vue.js

I am new to Vuejs. How can I get a message when a div in Datatable vuejs reach the bottom of its page. It will be really helpful when someone helps me out.

I am posting the answer for this question which i got it correctly. Actually i got ideas from someones comment in this question, which i am not able to see it now.
Adding code:
mounted() {
let box = document.querySelector(".v-data-table__wrapper");
// #ts-ignore
box.addEventListener("scroll", this.scrollHandler);
}
/*
* Infinite scroll event
*/
scrollHandler(e) {
// #ts-ignore
let context = this.$store.state[this.$options.parent.fileName];
if (!context.lazyLoading.enabled) {
return;
}
let el = e.srcElement;
// #ts-ignore
this.reachedBottom = false;
// #ts-ignore
let context = this.$store.state[this.$options.parent.fileName];
// #ts-ignore
if (!this.reachedBottom) {
if (el.scrollTop >= (el.scrollHeight - el.clientHeight) - 100) {
// #ts-ignore
this.reachedBottom = true;
if (context.lazyLoading.enabled && context.lazyRecords && context.lazyRecords.length > 0)
context.formData = context.lazyRecords.slice(0, (context.formData.length + (context.lazyLoading.initialRecordLoad || context.dashboard.lazyLoading.initialRecordLoad)));
else if (!context.lazyLoading.enabled)
context.formData = context.copyData.slice(0, (context.formData.length + (context.lazyLoading.initialRecordLoad || context.dashboard.lazyLoading.initialRecordLoad)));
}
}
this.$nextTick(() => {
// #ts-ignore
this.reachedBottom = false;
});
}

Related

Cant receive data from postMessage in react native webview

here is my injected js:
window.ReactNativeWebView.postMessage(JSON.stringify({
external_url_open: null,
height: Math.max(document.body.offsetHeight, document.body.scrollHeight, document.documentElement.clientHeight)
}));
(function(){
var attachEvent = function(elem, event, callback)
{
...
}
var all_links = document.querySelectorAll('a[href]');
if ( all_links ) {
for ( var i in all_links ) {
if ( all_links.hasOwnProperty(i) ) {
attachEvent(all_links[i], 'onclick', function(e){
if ( new RegExp( '^https?:\/\/www.dropbox\.com.*', 'gi' ).test( this.href ) ) {
// handle external URL
e.preventDefault();
window.ReactNativeWebView.postMessage(JSON.stringify({
external_url_open: this.href,
}));
}
else { window.location.href = this.href; }
});
}
}
}
})();
I want to receive the pages height on react native side with this code:
<WebView
...
javascriptEnabled={true}
onMessage={(event) => {
// retrieve event data
var data = event.nativeEvent.data; // maybe parse stringified JSON
try {
data = JSON.parse(data)
} catch ( e ) { }
// check if this message concerns us
if ( 'object' == typeof data && data.external_url_open ) {
if (data.external_url_open != null){
// proceed with URL open request
Linking.openURL(data.external_url_open);
}
else {
height = data.height;
console.log(data.page_height);
}
}
}}
injectedJavaScript={jsCode}
...
/>
the link handling part works but the height receive part doesn't and I dont see anything in console when refreshing the page. Can anyone help?
I just needed to relocate this else to the outer if:
else {
height = data.height;
console.log(data.page_height);
}

Hide/Show the corresponding data from the chart on legend click ngx-charts

I am working with angular 6 and ngx-chart and I need on clicking the legend item, the corresponding data from the chart should show/hide
The ng-chart library does have this functionality and my client requests it.
Edit01:
I have almost everything working but I have a problem when applying axisFormat. once I remove an item from the legend it reformats the x-axis and doesn't literally put how the data comes without applying the AxisFormat. Any solution?
onSelect (event) {
let temp = JSON.parse(JSON.stringify(this.multi));
this.sourceData = JSON.parse(JSON.stringify(this.multi2));
if (this.isDataShown(event)) {
//Hide it
temp.some(pie => {
const pie2 = pie.name[0] + ',' + pie.name[1];
// console.log('pie', pie[0], event, pie2);
if (pie2 === event) {
pie.series = [];
return true;
}
});
} else {
//Show it back
console.log('Entramos en el ELSE');
const pieToAdd = this.sourceData.filter(pie => {
const pie2 = pie.name[0] + ',' + pie.name[1];
return pie2 === event;
});
temp.some(pie => {
const pie2 = pie.name[0] + ',' + pie.name[1];
if (pie2 === event) {
pie.series = pieToAdd[0].series;
return true;
}
});
}
console.log('log temp: ' + JSON.stringify(temp));
this.multi = temp;
// this.axisFormat(this.multi);
}
isDataShown = (name) => {
const selectedPie = this.multi.filter(pie => {
const pie2 = pie.name[0] + ',' + pie.name[1];
return pie2 === name && pie.series[0] !== undefined;
});
return selectedPie && selectedPie.length > 0;
}
axisFormat(val) {
const options = { day: 'numeric', month: 'short', hour: '2-digit', minute: '2-digit' };
// Esto funciona pero al hacer timeline no pone horas val.toLocaleDateString("es-ES", options);
console.log('val:', val.toLocaleDateString('es-ES', options));
return val.toLocaleDateString('es-ES', options);
}
HTML
<ngx-charts-line-chart [view]="" [scheme]="colorScheme" [results]="multi" [gradient]="gradient" [xAxis]="showXAxis" [yAxis]="showYAxis" [legend]="showLegend" legendPosition="'below'" [showXAxisLabel]="showXAxisLabel" [showYAxisLabel]="showYAxisLabel"
[xAxisLabel]="xAxisLabel" [yAxisLabel]="yAxisLabel" [autoScale]="autoScale" [timeline]="timeline" [roundDomains]="true" [animations]="animations" (select)="onSelect($event)" [xAxisTickFormatting]="axisFormat">
<ng-template #seriesTooltipTemplate let-items="model">
<p>{{items[0].name | date:'medium'}}</p>
<ul>
<li *ngFor="let item of items">
{{item.series}}: {{item.value | number}}
</li>
</ul>
</ng-template>
</ngx-charts-line-chart>
EDIT
Hello,
I have already managed to solve the problem adding an example in case it can help other people.
https://stackblitz.com/edit/click-lengd-ngx-charts
I am kinda new to Stack Overflow, but i think you should specify your answer more and show us what you already tried. Nevertheless I will try to help you.
You should give your chart a (select)="onClickFunction ($event)" in HTML. In your TS you then call the onClickFunction(event). I always start with giving it a console.log(event) to see what i get from clicking on the legend.
After clicking on the legend, you get the label of the element you clicked on. You can then search for this label in your data and remove this data out of the array you use for filling the chart.
If you provide a stackblitz or plunker wtih your code, I will gladly show you how to do it.
This is how we can achieve it for ngx-pie-chart. With the help of select event, capture it, identify the item from the data and make it zero. Next, on the next click, add the value back from the source copy. See it working here ngx-pie-chart label-filter
onSelect (event) {
let temp = JSON.parse(JSON.stringify(this.single));
if (this.isDataShown(event)) {
//Hide it
temp.some(pie => {
if (pie.name === event) {
pie.value = 0;
return true;
}
});
} else {
//Show it back
const pieToAdd = this.sourceData.filter(pie => {
return pie.name === event;
});
temp.some(pie => {
if (pie.name === event) {
pie.value = pieToAdd[0].value;
return true;
}
});
}
this.single = temp;
}
isDataShown = (name) => {
const selectedPie = this.single.filter(pie => {
return pie.name === name && pie.value !== 0;
});
return selectedPie && selectedPie.length > 0;
}

React-native flatlist to keep scrolling while touching view

I am trying to implement a drag and drop solution in react-native and I want to make my flatlist scroll if I drag an item in the upper 10 percent and bottom 10 percent of the view. So far the only way i can get it to happen is by calling a function that recursively dispatches a this._flatList.scrollToOffset({ offset, animated: false });. The recursive call stops when a certain condition is met but the scrolling effect is choppy. Any advice on making that smoother?
// on move pan responder
onPanResponderMove: Animated.event([null, { [props.horizontal ? 'moveX' : 'moveY']: this._moveAnim }], {
listener: (evt, gestureState) => {
const { moveX, moveY } = gestureState
const { horizontal } = this.props
this._move = horizontal ? moveX : moveY;
const { pageY } = evt.nativeEvent;
const tappedPixel = pageY;
const topIndex = Math.floor(((tappedPixel - this._distanceFromTop + this._scrollOffset) - this._containerOffset) / 85);
const bottomIndex = Math.floor(((tappedPixel + (85 - this._distanceFromTop) + this._scrollOffset) - this._containerOffset) / 85);
this.setTopAndBottom(topIndex, bottomIndex);
this.scrolling = true;
this.scrollRec();
}
}),
// recursive scroll function
scrollRec = () => {
const { activeRow } = this.state;
const { scrollPercent, data, } = this.props;
const scrollRatio = scrollPercent / 100;
const isLastItem = activeRow === data.length - 1;
const fingerPosition = Math.max(0, this._move - this._containerOffset);
const shouldScrollUp = fingerPosition < (this._containerSize * scrollRatio); // finger is in first 10 percent
const shouldScrollDown = !isLastItem && fingerPosition > (this._containerSize * (1 - scrollRatio)) // finger is in last 10
const nextSpacerIndex = this.getSpacerIndex(this._move, activeRow);
if (nextSpacerIndex >= this.props.data.length) { this.scrolling = false; return this._flatList.scrollToEnd(); }
if (nextSpacerIndex === -1) { this.scrolling = false; return; }
if (shouldScrollUp) this.scroll(-20);
else if (shouldScrollDown) this.scroll(20);
else { this.scrolling = false; return; };
setTimeout(this.scrollRec, 50);
}
/
Yeah, pass an options object to your Animated.event with your listener with useNativeDriver set to true
Animated.event([
null,
{ [props.horizontal ? "moveX" : "moveY"]: this._moveAnim },
{
listener: ...,
useNativeDriver: true
}
]);
Should make things significantly smoother.
edit: I feel I should add that there is probably a saner way to accomplish this, are you only using a FlatList because of it's "infinite" dimensions?

Primeng loading icon is not updating

I am using primeng turbo table with lazy loading and enabled loading to attribute it's not getting updated even got updated
<p-table #dt [loading]="loader" [columns]="cols" [value]="datasource.merchants" [rows]="perPage" [paginator]="true" [pageLinks]="5"
[lazy]="true" [totalRecords]="datasource.totalCount" (onLazyLoad)="loadLazyData($event)" [exportFilename]="'merchant-list'">
.....
Script
loadLazyData(event: LazyLoadEvent) {
if (event.first !== this.searchParams.offset || event.rows !== this.searchParams.limit) {
this.loader = true;
this.searchParams.offset = event.first;
this.searchParams.limit = event.rows;
this.apiService.getResponse(this.smartSearchParams.query, event.first, event.rows)
.subscribe((result) => {
this.datasource = result;
let newArray = result.merchants.slice();
this.dataTable.value = newArray;
setTimeout(() => {
this.loader = false;
this.dataTable.loading = this.loader;
});
}, (err: any) => {
setTimeout(() => {
this.loader = false;
this.dataTable.loading = this.loader;
});
});
}
can someone help me with this issue
The issue is with changeDetection for the component.
I have removed the changeDetection:ChangeDetectionStrategy.OnPush from my component its started working

Visiting multiple urls using PhantomJS evaluating Error

I have this beautiful code, all I want to make some pause between visits, so I add a 'setinterval', but this not works:
var page = require('webpage').create();
// the urls to navigate to
var urls = [
'http://blogger.com/',
'https://github.com/',
'http://reddit.com/'
];
var i = 0;
// the recursion function
var genericCallback = setInterval(function () {
return function (status) {
console.log("URL: " + urls[i]);
console.log("Status: " + status);
// exit if there was a problem with the navigation
if (!status || status === 'fail') phantom.exit();
i++;
if (status === "success") {
//-- YOUR STUFF HERE ----------------------
// do your stuff here... I'm taking a picture of the page
page.render('example' + i + '.png');
//-----------------------------------------
if (i < urls.length) {
// navigate to the next url and the callback is this function (recursion)
page.open(urls[i], genericCallback());
} else {
// try navigate to the next url (it is undefined because it is the last element) so the callback is exit
page.open(urls[i], function () {
phantom.exit();
});
}
}
};
},2000);
// start from the first url
page.open(urls[i], genericCallback());
the screenshot with the error I get:
maybe someone could help me and heal this code? Because I'm new to JS and to PhantomJS, any help will be apreciate.
I got this code from another stackoverflow answer here - Using Multiple page.open in Single Script
but I can't comment to the author , because I don't have 50 reputation
It should rather be something like this:
var page = require('webpage').create();
var urls = ['http://blogger.com/','https://github.com/','http://reddit.com/'];
var i = 0;
function OpenPage(){
setTimeout(function(){
page.open(urls[i], function(status) {
if (status == 'success') {
page.render('example' + i + '.png');
}
i++;
if(i <= urls.length - 1){
OpenPage();
}else{
phantom.exit();
}
});
},2000);
}
OpenPage();