angular-soundmanager2 - how to rebuild the playlist? - angularjs

This is library I use.
For rebuilding playlist I do following:
angularPlayer.clearPlaylist(function () {
angular.forEach($scope.filtered, function (value) {
//$scope.$apply(function () {
angularPlayer.addTrack(value);
//});
});
});
Firstly, I clear playlist by function angularPlayer.clearPlaylist.
After I add all tracks in loop using angularPlayer.addTrack.
At the end I try to play playlist:
angularPlayer.play();
But it does now work. I checked console Chrome there are not errors.

I tried some ways and have invite solution, may be it will be useful for someone:
$scope.play = function (genre) {
$timeout(function () {
angularPlayer.stop();
angularPlayer.setCurrentTrack(null);
angularPlayer.clearPlaylist(function () {
if (genre !== undefined) {
$scope.filtered = filterFilter($scope.songs, {'genre': genre});
} else {
$scope.filtered = $scope.songs;
}
if (random) {
$scope.filtered = $filter('shuffleArray')($scope.filtered);
}
if ($scope.filtered.length == 0) {
console.log("No songs by genre " + genre);
}
angular.forEach($scope.filtered, function (value) {
angularPlayer.addTrack(value);
});
angularPlayer.play();
});
});
};

Related

Is possible use webkitRequestFileSystem from a Service Worker?

My idea is use an <input type="file"> to upload file, then troughth webkitRequestFileSystem save to FileSystem like this...
body.innerHTML = `<input type="file">`;
body.children[0].addEventListener("change", copyFiles);
...
function copyFiles() {
for (var i = 0; i < this.files.length; i++) {
(function (f) {
navigator.webkitPersistentStorage.queryUsageAndQuota(function (usage, granted) {
if ((granted - usage) < f.size) {
navigator.webkitPersistentStorage.requestQuota((granted + f.size), function () {
createFile(f);
}, errorHandler);
} else {
createFile(f);
}
});
})(this.files[i]);
}
}
...
function createFile(file) {
window.webkitRequestFileSystem(window.PERSISTENT, (file.size * 1.1), function (fileManager) {
fileManager.root.getFile(file.name, {create: true, exclusive: true}, function (fileEntry) {
fileEntry.createWriter(function (fileWriter) {
fileWriter.write(file);
}, errorHandler);
}, errorHandler);
}, errorHandler);
}
And it works, now I want use service worker to read and send little packets of contents of these files to my backend.
I'm new on Service Workers and I tried but I got self.webkitRequestFileSystem is not a function
Service Worker activation...
window.addEventListener("load", function () {
if ('serviceWorker' in navigator) {
window.addEventListener("message", function(e){
console.log(e);
});
navigator.serviceWorker.register('js/swa.js').then(function (swr) {
swr.sync.register('syncTest');
}).catch(function (error) {
console.log(error);
});
} else {
console.log("Service Worker", "Not available.");
}
});
And ServiceWorker script
function getAllEntries(dirReader) {
var entries = dirReader.readEntries();
for (var i = 0, entry; entry = entries[i]; ++i) {
paths.push(entry.toURL()); // Stash this entry's filesystem: URL.
// If this is a directory, we have more traversing to do.
if (entry.isDirectory) {
getAllEntries(entry.createReader());
}
}
}
self.addEventListener('sync', function (event) {
try {
var fs = self.webkitRequestFileSystem(self.PERSISTENT, 1024 * 1024 /*1MB*/);
getAllEntries(fs.root.createReader());
self.postMessage({entries: paths});
} catch (e) {
console.log(e);
}
});

Drift chat opening in every page

I have drift's async script code in the index.html file of the react app.
<script>
"use strict";
!function () {
var t = window.driftt = window.drift = window.driftt || [];
if (!t.init) {
if (t.invoked) return void (window.console && console.error && console.error("Drift snippet included twice."));
t.invoked = !0, t.methods = ["identify", "config", "track", "reset", "debug", "show", "ping", "page", "hide", "off", "on"],
t.factory = function (e) {
return function () {
var n = Array.prototype.slice.call(arguments);
return n.unshift(e), t.push(n), t;
};
}, t.methods.forEach(function (e) {
t[e] = t.factory(e);
}), t.load = function (t) {
var e = 3e5, n = Math.ceil(new Date() / e) * e, o = document.createElement("script");
o.type = "text/javascript", o.async = !0, o.crossorigin = "anonymous", o.src = "https://js.driftt.com/include/" + n + "/" + t + ".js";
var i = document.getElementsByTagName("script")[0];
i.parentNode.insertBefore(o, i);
};
}
}();
drift.SNIPPET_VERSION = '0.3.1';
drift.load('----api----');
drift.on('ready', api => {
api.widget.hide();
})
</script>
The issue is, it is getting popped up in every page of the app whereas I want it only when I click a button(onClick)
The function to trigger onClick :
openDriftChat = () =>{
const { setDriftState } = this.props;
if (window.drift.api) {
//this needs to happen only once but currently happening on every page load
if (!this.props.driftInit) {
if (localStorage.token) {
var tokenBase64 = localStorage.token.split(".")[1];
var tokenBase64_1 = tokenBase64.replace("-", "+").replace("_", "/");
var token = JSON.parse(window.atob(tokenBase64_1));
window.drift.identify(token.email, {
email: token.email,
nickname: token.name
});
setDriftState(true);
}
}
window.drift.api.openChat();
}
}
I basically want it pop up only when I call the function.
Hello I had the same issue:
To hide the welcome message use the following css code
iframe#drift-widget.drift-widget-welcome-expanded-online {
display: none !important;
}
iframe#drift-widget.drift-widget-welcome-expanded-away {
display: none !important;
}
The welcome message will only be shown when your drift button. Some extra info:
To hide the drift button icon use the following js code
drift.on('ready', function (api) {
api.widget.hide()
drift.on('message', function (e) {
if (!e.data.sidebarOpen) {
api.widget.show()
}
})
drift.on('sidebarClose', function (e) {
if (e.data.widgetVisible) {
api.widget.hide()
}
})
})
To call for the sidebar from a specific button use the following
Javascript
(function () {
var DRIFT_CHAT_SELECTOR = '.drift-open-chat'
function ready(fn) {
if (document.readyState != 'loading') {
fn();
} else if (document.addEventListener) {
document.addEventListener('DOMContentLoaded', fn);
} else {
document.attachEvent('onreadystatechange', function () {
if (document.readyState != 'loading')
fn();
});
}
}
function forEachElement(selector, fn) {
var elements = document.querySelectorAll(selector);
for (var i = 0; i < elements.length; i++)
fn(elements[i], i);
}
function openSidebar(driftApi, event) {
event.preventDefault();
driftApi.sidebar.open();
return false;
}
ready(function () {
drift.on('ready', function (api) {
var handleClick = openSidebar.bind(this, api)
forEachElement(DRIFT_CHAT_SELECTOR, function (el) {
el.addEventListener('click', handleClick);
});
});
});
})();
HTML
<a class="drift-open-chat">Open Chat</a>
I hope this helps someone out there.
PS: The above javascript code must be included after you have initialized your drift widget.
You need to disable that through the application: turn off the Playbooks.
Here is the link to do so: https://app.drift.com/playbooks
Hope it helps.

NodeJs note app delete function is not working?

I am building a Nodejs Note app and I am very new at this, so here the delete function doesn't work it, deletes everything from the array and I want to delete only title
There are two file app.js and note.js.
Here's the content of app.js file
if (command === "add") {
var note = notes.addNote(argv.title, argv.body);
if (note) {
console.log("Note created");
console.log("__");
console.log(`Title: ${note.title}`);
console.log(`Body: ${note.body}`);
} else {
console.log("The title has already exist")
}
} else if (command === "delete") {
var noteRemoved = notes.delNote(argv.title)
var message = noteRemoved ? "Note has been removed" : "Note not found";
console.log(message)
}
Here's the note.js content
var fetchNotes = function () {
try {
var noteString = fs.readFileSync("notes-data.json")
return JSON.parse(noteString);
} catch (e) {
return [];
}
};
var saveNotes = function (notes) {
fs.writeFileSync("notes-data.json", JSON.stringify(notes));
};
var addNote = function (title, body) {
var notes = fetchNotes();
var note = {
title,
body
};
var duplicateNotes = notes.filter(function (note) {
return note.title === title;
});
if (duplicateNotes.length === 0) {
notes.push(note);
saveNotes(notes);
return note;
};
}
var delNote = function (title) {
var notes = fetchNotes();
var filteredNotes = notes.filter(function (note) {
note.title !== title;
});
saveNotes(filteredNotes);
return notes.length !== filteredNotes.length
}
You miss return statement in delNote filter function
var filteredNotes = notes.filter(function (note) {
return note.title !== title;
});
or we can use es6 syntax:
const filteredNotes = notes.filter(note => note.title !== title);
You need to add return note.title !== title; in delNote function.

How to reuse functions in an AngularJS factory?

I have an AngularJS factory for some common local storage manipulation. It's a common set of functions against different variables. I am constructing it so that the functions are repeated depending on which variable needs to be manipulated. Likely not an elegant way to go about this so open to options.
The factory looks as follows. Is there a way to reuse functions depending on the variable without so much code bloat?
angular.module('app.datastore', [])
.factory('DataStore', function() {
var venue = angular.fromJson(window.localStorage['venue'] || '[]');
var prize = angular.fromJson(window.localStorage['prize'] || '[]');
function persist_venue() {
window.localStorage['venue'] = angular.toJson(venue);
}
return {
list_venue: function () {
return venue;
},
get_venue: function(venueId) {
for (var i=0; i<venue.length; i++) {
if (venue[i].id === venueId) {
return venue[i];
}
}
return undefined;
},
create_venue: function(venueItem) {
venue.push(venueItem);
persist_venue();
},
list_prize: function () {
return prize;
},
get_prize: function(prizeId) {
for (var i=0; i<prize.length; i++) {
if (prize[i].id === prizeId) {
return prize[i];
}
}
return undefined;
},
create_prize: function(prizeItem) {
venue.push(prizeIem);
persist_prize();
}
};
});
My approach is to return in the factory a function which will return a store of a type (venue, prize, ...)
angular.module('app.datastore', [])
.factory('DataStore', function () {
var getStoreFunction = function (storeName) {
var store = angular.fromJson(window.localStorage[storeName] || '[]');
function persist() {
window.localStorage[storeName] = angular.toJson(store);
};
return {
list: function () {
return store;
},
getItem: function (id) {
return store.find(function (elem) {
return elem.id === id;
});
},
createItem: function (item) {
store.push(item);
persist(store);
}
}
};
return { getStore : getStoreFunction };
});
you can create unlimited store by using
var venueStore = DataStore.getStore('venue');
//use of your store
venueStore.createItem({
id : venueStore.list().length + 1,
name : 'myVenue' + venueStore.list().length + 1
});
$scope.venues = venueStore.list();
you can create a factory per type if you want or use it directly in your controller as in this example : https://jsfiddle.net/royto/cgxfmv4q/
i dont know if your familiar with John Papa's angular style guide but you really should take a look it might help you with a lot of design questions.
https://github.com/johnpapa/angular-styleguide
anyway - i would recommend you use this approach -
angular.module('app.datastore', [])
.factory('DataStore', function () {
var venue = angular.fromJson(window.localStorage['venue'] || '[]');
var prize = angular.fromJson(window.localStorage['prize'] || '[]');
return {
list_venue: list_venue,
persist_venue: persist_venue,
get_venue: get_venue,
create_venue: create_venue,
list_prize: list_prize,
get_prize: get_prize,
create_prize: create_prize
};
function persist_venue() {
window.localStorage['venue'] = angular.toJson(venue);
}
function list_venue() {
return venue;
}
function get_venue(venueId) {
for (var i = 0; i < venue.length; i++) {
if (venue[i].id === venueId) {
return venue[i];
}
}
return undefined;
}
function create_venue(venueItem) {
venue.push(venueItem);
persist_venue();
}
function list_prize() {
return prize;
}
function get_prize(prizeId) {
for (var i = 0; i < prize.length; i++) {
if (prize[i].id === prizeId) {
return prize[i];
}
}
return undefined;
}
function create_prize(prizeItem) {
venue.push(prizeIem);
persist_prize();
} });
i like this approach because on the top you can see all the functions available in this factory nice and easy,
and you can also reuse every function you expose outside, inside also, so its very effective and organized,
hope that helped,
good luck.

Cordova backbutton preventDefault is not working

I have application which is done using ionicframework and cordova. In my app i have requirement that if user pressed back button then i need to ignore it. But only after user pressed it third time it should close app.
Previously project was done using phonegap and jquery and same code works. I did small workaround when i am throwing an exception then it app was not closed when it should not.
document.addEventListener("backbutton", function (e) {
if (new Date() - firstDateClick > 1000) {
firstDateClick = new Date();
totalClicks = 1;
} else {
totalClicks++;
if (totalClicks >= 3) {
var answer = confirm('Are You Sure You Want Exit');
if (answer) {
var service = angular.injector(['ng', 'starter.services']).get('DanceService');
service.logEvent("exit")
.then(function () {
alert('exit1')
if (navigator.app) {
navigator.app.exitApp();
}
else if (navigator.device) {
navigator.device.exitApp();
}
})
} else {
totalClicks = 1;
}
}
}
throw "ignore"
});
But i dont like idea to throw exception.
i made two times control before log out from the app. So the user can press one time and a toast will appear with the text "press again to exit" and the second press -> log out.
This is my service:
var deregisterFunction = null;
return {
disableBack: disableBack,
registerAction: registerAction,
goHome: goHome,
goBack: goBack,
deregisterAction: deregisterAction,
closeApp: closeApp
};
function disableBack() {
deregisterFunction = angular.copy($ionicPlatform.registerBackButtonAction(null, 101));
}
function registerAction(cb, priority) {
deregisterFunction = angular.copy($ionicPlatform.registerBackButtonAction(cb, priority));
}
function deregisterAction() {
if (deregisterFunction) {
deregisterFunction();
}
goBack();//default behaviour
}
function goHome() {
deregisterFunction = angular.copy($ionicPlatform.registerBackButtonAction(function() {
$state.go('app.home');
}, 101));
}
function goBack() {
deregisterFunction = angular.copy($ionicPlatform.registerBackButtonAction(function() {
$ionicHistory.goBack();
}, 101));
}
function closeApp() {
deregisterFunction = angular.copy($ionicPlatform.registerBackButtonAction(function() {
ionic.Platform.exitApp();
}, 101));
}
And this my utils service:
var service = {
logoutToast: logoutToast,
resetToastCount: resetToastCount
};
var toastCount = 0;
return service;
function resetToastCount() {
toastCount = 0;
}
function logoutToast() {
switch (toastCount) {
case 0:
$cordovaToast.show('Press again to log out', 'short', 'bottom');
toastCount++;
break;
case 1:
toastCount = 0;
//logout
break;
default:
$cordovaToast.show('Error', 'short', 'bottom');
}
}
}
}());
So in my controller i have this for register the action of my service:
$scope.$on('$ionicView.afterEnter', backButtonService.registerAction(utils.logoutToast, 101));
This for reset the count where i want:
$scope.$on('$ionicView.afterEnter', utils.resetToastCount());
And this for deregister my action when i navigate:
$scope.$on('$stateChangeStart', backButtonService.deregisterAction);
Hope this will helps you :)
Disable back button on Ionic/Cordova
$ionicPlatform.registerBackButtonAction(null, 101);

Resources