: str_replace(): Passing null to parameter #2 ($replace) of type array|string is deprecated in
var sel = container.data('prop').replace(/-\d+/, '');
var $targ = $preview.find('[data-preview*="' + sel + '"]');
var $inp = container.data('input');
var prop = $inp.attr('data-prop');
$inp.trigger('colorpicker-change');
if (!$targ.length) return;
if (prop === 'box-shadow') pre = '0 1px 4px 0 ';
//console.log(this, $t.attr('data-overrideProp') || prop)
var col = color.tiny.toRgbString();
$t.css($t.attr('data-overrideProp') || prop, pre + col)
FlowFlow.switchToView('list');
updateModel: function(event) {
var $t = $(event.target);
var name = $t.attr('name');
val = $t.is(':checked') ? ($t.attr('value') || 'yep') : 'nope'
if ($t.is(':checkbox')) {
$group = this.$el.find('[name="' + name + '"]');
$group.each(function () {
if (this.checked) val[cbVal] = 'yep';
val = $t.is(':checked') ? 'yep' : 'nope';
this.trigger('changeModel', {name: name.replace('stream-' + (this.model.get('id') || 'new') + '-', ''), val: val })
saveViaAjax: function ( e ) {
console.log('save stream');
if ( e ) e.stopImmediatePropagation();
var wasEmptyList = streamRowModels.length === 0;
var $t = $(e ? e.target : '');
var isNew = this.model.isNew();
if ($t.is('[id^=networks-sbmt]')) {
if (!this.validateFeedCfg($t)) return false;
FlowFlow.makeOverlayTo('show');
$t.addClass('button-in-progress');
var promise = this.model.save(isNew);
promise.done(function(serverModel){
if (serverModel.error) return;
FlowFlow.makeOverlayTo('hide');
self.rowModel = new StreamRowModel( { cloud : serverModel.cloud });
self.rowView = new StreamRowView({model: self.rowModel});
streamRowModels.add(self.rowModel);
FlowFlow.$list.append(self.rowView.$el);
self.$el.removeClass('stream-view-new');
self.rowModel.set('id', serverModel.id);
self.model.trigger('stream-saved');
FlowFlow.$list.find('.empty-row').remove();
sessionStorage.setItem('ff_stream', serverModel.id);
$t.addClass('updated-button').html('<i class="flaticon-check_mark" data-action="edit"></i> Updated');
$t.removeClass('button-in-progress');
setTimeout( function () {
$t.html('Save changes').removeClass('updated-button');
alert('Something went wrong. Please try to reload page. If this repeats please contact support at https://social-streams.com/contact/')
showPreview: function (e) {
FlowFlow.makeOverlayTo('show');
'action' : 'flow_flow_show_preview',
}).success(function(response){
var $popup = $('.content-popup');
FlowFlow.makeOverlayTo('hide');
$body.css('overflow', 'hidden');
$popup.off(transitionEnd).addClass('is-visible').find('.content-popup__content').html(response);
if (FlowFlow.$previewStyles) {
FlowFlow.$previewStyles.appendTo('head');
$popup.on('click', function(event){
if( $(event.target).is('.content-popup__close') || $(event.target).is('.content-popup') ) {
$(this).removeClass('is-visible');
$popup.on(transitionEnd, function(){
$popup.find('.content-popup__content').html('').off(transitionEnd);
$body.find('.ff-slideshow').remove();
if (!FlowFlow.$previewStyles) {
FlowFlow.$previewStyles = $('#ff_style, #ff_ad_style');
FlowFlow.$previewStyles.detach();
$body.css('overflow', '');
FlowFlow.makeOverlayTo('hide');
alert('Something went wrong. Please try again after page refresh')
FeedsModel = Backbone.Model.extend({
console.log('initialize Feeds Model', this);
save: function( isNew ) {
action: la_plugin_slug_down + '_save_sources_settings',
// filter and send only changed
var feeds = $params.data.model.feeds;
var feedsChanged = $params.data.model.feeds_changed;
var created, changed = {}, id; // created can be only single;
for (feed in feedsChanged) {
id = feedsChanged[feed]['id'];
feedsToSend[id] = feeds[id];
if (feedsChanged[feed]['state'] === 'created') {
created = feedsChanged[feed];
$params.data.model.feeds = feedsToSend;
var array = $.map( _.clone( feeds ), function(value, index) {
if ( array.length > 1 ) {
array.unshift(array.pop());
for (var i = 0; i < array.length; ++i) {
newObj[array[i]['id']] = array[i];
self.set('feeds', newObj);
return Backbone.sync( 'create', this, $params ).done(function( serverModel ){
if ( serverModel && serverModel.error ) {
var promise = FlowFlow.popup( serverModel.error == 'not_allowed' ? 'Nay! You have no permissions to do this, please contact admin.' : 'Nay! Something went wrong, please contact support', false, 'alert');
FlowFlow.makeOverlayTo('hide');
if (self.isNew() && serverModel && serverModel['id']) {
self.set('id', serverModel['id']);
// todo in next updates update stream status when error resolved in feed
if (serverModel && serverModel['feeds']) {
for (var feed in serverModel['feeds']) {
id = serverModel['feeds'][feed]['id'];
feeds[id] = serverModel['feeds'][feed];
"click .submit-button": "saveViaAjax",
"keyup input, textarea": "catchEnter",
"keyup #feeds-search": "filterFeedsByName",
"click .button-add": "addFeedStepOne",
"click .flaticon-tool_more": "toggleDropDown",
"mouseleave .controls": "popupLeave",
"click [data-action='filter']": "filterFeed",
"click [data-action='cache']": "resetFeedCache",
"click [data-action='check']": "checkStreams",
"click .flaticon-tool_delete": "deleteFeed",
"click .tr-error": "hideError",
"click .button-go-back": "goBackToFeedChoice",
"click .networks-list > li": "createFeedView",
"click .popup .button-cancel-action, .popupclose": "closeFeedPopup",
"click .ff-toggle-display": "toggleErrorFeeds",
"click .ff-search-display": "toggleFilterInput",
"keyup [data-action='add-filter']": "addFilter",
"click [data-action='delete-filter']": "deleteFilter",
"change .feed-view input": "updateModel",
"change .feed-view select": "updateModel",
"change td .switcher": "toggleFeed",
"mouseenter .td-status": "showErrorIfPresent",
"mouseleave .td-status": "hideError",
if ( plugin == 'insta_flow' ) {
feedsViewEvents[ "click .flaticon-tool_edit, .td-feed, .td-info .highlight"] = "editFeed";
feedsViewEvents[ "click .button-add" ] = "createFeedView";
feedsViewEvents[ "click .flaticon-tool_edit, .td-feed"] = "editFeed"
FeedsView = Backbone.View.extend({
renderedFirstTime: false,
currentPage: parseInt( sessionStorage.getItem('ff_feeds_page') || 1) ,
showErrorFeedsOnly: false,
this.$tab = $('#sources-tab');
this.$popup = this.$el.find('.popup');
this.renderedFirstTime = true;
// todo broadcast to boost element
this.model.listenTo(this, 'changeFeedInModel', function (data){
console.log('changeFeedInModel event', data);
var feeds = self.model.get('feeds');
var feed = feeds[data.id];
feed[data.name] = data.val;
var feeds = this.model.get('feeds');
var changed = this.model.get( 'feeds_changed' ), prop, state;
console.log( 'RENDER VIEWS', JSON.stringify( changed ) );
if ( ! this.renderedFirstTime ) {
action: la_plugin_slug_down + '_sources',
var sourcesRequest = $.post( vars.ajaxurl, data ).done( function( res ) {
feeds = JSON.parse( res );
console.log( 'Error parsing feeds JSON' );
if ( _.isEmpty( feeds ) ) feeds = {};
self.model.set( 'feeds', feeds );
self.renderedFirstTime = true;
if ( plugin == 'insta_flow' ) {
$( document ).trigger( 'feeds-loaded', feeds )
// if nothing changed it's first time or hard re-render
console.log( 'renderBoostsUI first time')
var boostsRequest = FlowFlow.renderBoostsUI( self.model );
$( document ).trigger( 'feeds-loaded', feeds )
$.when( boostsRequest ).then( function onSuccess ( boostsData ) {
boosts = JSON.parse( boostsData );
console.log( 'boosts data parsing error', e );
var plansRequest = $.get( 'https://api.flowflowapp.com/api/v1/flow-flow/ff?action=plans' + ( FlowFlow.subscription && FlowFlow.subscription.plan_id ? '&active_plan=' + FlowFlow.subscription.plan_id : '' ) );
$.when( plansRequest ).then( function onSuccess ( plansData ) {
FlowFlow.renderBoostPricingTable( plans, boosts );
console.log( 'plans UI error', arguments );
console.log( 'boosts UI error', arguments );
$( document ).on( 'list-nav', function ( e, data ) {
if ( data && data.page && data.page != self.currentPage ) {
self.currentPage = data.page;
self.renderFeedsList( changed, self.showErrorFeedsOnly );
self.savePage( data.page );
_renderUI( feeds, changed );
function _renderUI( feeds, changed ) {
_.each( feeds, function ( feed ) {
views += _.template(templates[feed.type + 'View'])({
filterViews += _.template(templates['filterView'])({
self.$el.find( '#feed-views' ).html( views );
self.$el.find( '#filter-views' ).html( filterViews );
_.each( changed, function ( feed ) {
// if created or changed, views already exist
if ( feed.state == 'deleted' ) {
self.$el.find( '.feed-view[data-uid="' + feed.id + '"], .feed-view[data-filter-uid="' + feed.id + '"]' ).remove();
_.each( feeds, function ( feed, id, feedsHash ) {
var page = Math.floor(index / 8);
self.renderFeedsList( changed, self.showErrorFeedsOnly );
if ( self.errorsPresent ) {
self.$tab.addClass('errors-present');
self.$tab.removeClass('errors-present');
self.paginator = self.initPaginator( self.currentPage );
console.log('current page', self.currentPage )
if ( _.find( changed , function ( item ) { return item.state === 'created' } ) ) {
if ( self.currentPage ) {
self.paginator.paginate( typeof self.currentPage === 'number' ? self.currentPage : 1 );
// self.currentPage = false;
savedPage = parseInt( sessionStorage.getItem('ff_feeds_page') || 1) ;
self.paginator.paginate( savedPage );
self.currentPage = savedPage;
sessionStorage.setItem( 'ff_feeds_page', -1 ); // one time