PageSourceSearch

https://superfly.fm/plugins/system/smartappbanner/js/jquery.smartbanner.js

js superfly.fm collected 2026-10-02 03:09:08 UTC 9,468 bytes, 192 lines download raw bytes

1/*!
2 * jQuery Smart Banner
3 * Copyright (c) 2012 Arnold Daniels <[email protected]>
4 * Based on 'jQuery Smart Web App Banner' by Kurt Zenisek @ kzeni.com
5 */
6!function ($) {
7    var SmartBanner = function (options) {
8        this.origHtmlMargin = parseFloat($('html').css('margin-top')) // Get the original margin-top of the HTML element so we can take that into account
9        this.options = $.extend({}, $.smartbanner.defaults, options)
10
11        var standalone = navigator.standalone // Check if it's already a standalone web app or running within a webui view of an app (not mobile safari)
12        var UA = navigator.userAgent
13          
14        // Detect if agent is Android device or display forced
15        if (this.options.force) {
16            this.type = this.options.force;
17        } 
18        if (UA.match(/Android/i) != null) {
19            this.type = 'android';
20        }
21
22        // Don't show banner if device isn't iOS or Android, website is loaded in app or user dismissed banner
23        if (!this.type || standalone || this.getCookie('sb-closed') || this.getCookie('sb-installed')) {
24            return
25        }
26
27        // Calculate scale
28        this.scale = this.options.scale == 'auto' ? $(window).width() / window.screen.width : this.options.scale
29        if (this.scale < 1) this.scale = 1
30
31        // Get info from meta data
32        var meta = $(this.type == 'android' ? 'meta[name="google-play-app"]' :
33            this.type == 'ios' ? 'meta[name="apple-itunes-app"]' : 'meta[name="msApplication-ID"]');
34        if (meta.length == 0) return
35
36        // For Windows Store apps, get the PackageFamilyName for protocol launch
37        if (this.type == 'windows') {
38            this.pfn = $('meta[name="msApplication-PackageFamilyName"]').attr('content');
39            this.appId = meta.attr('content')[1]
40        } else {
41            this.appId = /app-id=([^\s,]+)/.exec(meta.attr('content'))[1]
42        }
43
44        this.title = this.options.title ? this.options.title : $('title').text().replace(/\s*[|\-·].*$/, '')
45        this.author = this.options.author ? this.options.author : ($('meta[name="author"]').length ? $('meta[name="author"]').attr('content') : window.location.hostname)
46
47        // Create banner
48        this.create()
49        this.show()
50        this.listen()
51    }
52
53    SmartBanner.prototype = {
54
55        constructor: SmartBanner
56    
57      , create: function() {
58            var iconURL
59              , link=(this.options.url ? this.options.url : (this.type == 'windows' ? 'ms-windows-store:PDP?PFN=' + this.pfn : (this.type == 'android' ? 'market://details?id=' : 'https://itunes.apple.com/' + this.options.appStoreLanguage + '/app/id')) + this.appId)
60              , inStore=this.options.price ? this.options.price + ' - ' + (this.type == 'android' ? this.options.inGooglePlay : this.type == 'ios' ? this.options.inAppStore : this.options.inWindowsStore) : ''
61              , gloss=this.options.iconGloss === null ? (this.type=='ios') : this.options.iconGloss
62
63            $('body').prepend('<div id="smartbanner" class="'+this.type+'"><div class="sb-container"><a href="#" class="sb-close">&times;</a><span class="sb-icon"></span><div class="sb-info"><strong>'+this.title+'</strong><span>'+this.author+'</span><span>'+inStore+'</span></div><a href="'+link+'" class="sb-button"><span>'+this.options.button+'</span></a></div></div>')
64            
65            if (this.options.icon) {
66                iconURL = this.options.icon
67            } else if ($('link[rel="apple-touch-icon-precomposed"]').length > 0) {
68                iconURL = $('link[rel="apple-touch-icon-precomposed"]').attr('href')
69                if (this.options.iconGloss === null) gloss = false
70            } else if ($('link[rel="apple-touch-icon"]').length > 0) {
71                iconURL = $('link[rel="apple-touch-icon"]').attr('href')
72            } else if ($('meta[name="msApplication-TileImage"]').length > 0) {
73              iconURL = $('meta[name="msApplication-TileImage"]').attr('content')
74            } else if ($('meta[name="msapplication-TileImage"]').length > 0) { /* redundant because ms docs show two case usages */
75              iconURL = $('meta[name="msapplication-TileImage"]').attr('content')
76            }
77            
78            if (iconURL) {
79                $('#smartbanner .sb-icon').css('background-image','url('+iconURL+')')
80                if (gloss) $('#smartbanner .sb-icon').addClass('gloss')
81            } else{
82                $('#smartbanner').addClass('no-icon')
83            }
84
85            this.bannerHeight = $('#smartbanner').outerHeight() + 2
86
87            if (this.scale > 1) {
88                $('#smartbanner')
89                    .css('top', parseFloat($('#smartbanner').css('top')) * this.scale)
90                    .css('height', parseFloat($('#smartbanner').css('height')) * this.scale)
91                $('#smartbanner .sb-container')
92                    .css('-webkit-transform', 'scale('+this.scale+')')
93                    .css('-msie-transform', 'scale('+this.scale+')')
94                    .css('-moz-transform', 'scale('+this.scale+')')
95                    .css('width', $(window).width() / this.scale)
96            }
97        }
98        
99      , listen: function () {
100            $('#smartbanner .sb-close').on('click',$.proxy(this.close, this))
101            $('#smartbanner .sb-button').on('click',$.proxy(this.install, this))
102        }
103        
104      , show: function(callback) {
105            $('#smartbanner').stop().animate({top:0},this.options.speedIn).addClass('shown');
106			$('body').stop().animate({marginTop:this.origHtmlMargin+(this.bannerHeight*this.scale)},this.options.speedIn,'swing',callback);
107        }
108        
109      , hide: function(callback) {
110            $('#smartbanner').stop().animate({top:-1*this.bannerHeight*this.scale},this.options.speedOut).removeClass('shown');
111			$('body').stop().animate({marginTop:this.origHtmlMargin},this.options.speedOut,'swing',callback);
112        }
113      
114      , close: function(e) {
115            e.preventDefault()
116            this.hide()
117            this.setCookie('sb-closed','true',this.options.daysHidden)
118        }
119       
120      , install: function(e) {
121            this.hide()
122            this.setCookie('sb-installed','true',this.options.daysReminder)
123        }
124       
125      , setCookie: function(name, value, exdays) {
126            var exdate = new Date()
127            exdate.setDate(exdate.getDate()+exdays)
128            value=escape(value)+((exdays==null)?'':'; expires='+exdate.toUTCString())
129            document.cookie=name+'='+value+'; path=/;'
130        }
131        
132      , getCookie: function(name) {
133            var i,x,y,ARRcookies = document.cookie.split(";")
134            for(i=0;i<ARRcookies.length;i++) {
135                x = ARRcookies[i].substr(0,ARRcookies[i].indexOf("="))
136                y = ARRcookies[i].substr(ARRcookies[i].indexOf("=")+1)
137                x = x.replace(/^\s+|\s+$/g,"")
138                if (x==name) {
139                    return unescape(y)
140                }
141            }
142            return null
143        }
144      
145      // Demo only
146      , switchType: function() {
147          var that = this
148
149          this.hide(function () {
150              that.type = that.type == 'android' ? 'ios' : 'android'
151              var meta = $(that.type == 'android' ? 'meta[name="google-play-app"]' : 'meta[name="apple-itunes-app"]').attr('content')
152              that.appId = /app-id=([^\s,]+)/.exec(meta)[1]
153
154              $('#smartbanner').detach()
155              that.create()
156              that.show()
157          })
158      }
159    }
160
161    $.smartbanner = function (option) {
162        var $window = $(window)
163        , data = $window.data('typeahead')
164        , options = typeof option == 'object' && option
165        if (!data) $window.data('typeahead', (data = new SmartBanner(options)))
166        if (typeof option == 'string') data[option]()
167    }
168
169    // override these globally if you like (they are all optional)
170    $.smartbanner.defaults = {
171        title: null, // What the title of the app should be in the banner (defaults to <title>)
172        author: null, // What the author of the app should be in the banner (defaults to <meta name="author"> or hostname)
173        price: 'FREE', // Price of the app
174        appStoreLanguage: 'us', // Language code for App Store
175        inAppStore: 'On the App Store', // Text of price for iOS
176        inGooglePlay: 'In Google Play', // Text of price for Android
177        inWindowsStore: 'In the Windows Store', //Text of price for Windows
178        icon: null, // The URL of the icon (defaults to <meta name="apple-touch-icon">)
179        iconGloss: null, // Force gloss effect for iOS even for precomposed
180        button: 'VIEW', // Text for the install button
181        url: null, // The URL for the button. Keep null if you want the button to link to the app store.
182        scale: 'auto', // Scale based on viewport size (set to 1 to disable)
183        speedIn: 300, // Show animation speed of the banner
184        speedOut: 400, // Close animation speed of the banner
185        daysHidden: 15, // Duration to hide the banner after being closed (0 = always show banner)
186        daysReminder: 90, // Duration to hide the banner after "VIEW" is clicked *separate from when the close button is clicked* (0 = always show banner)
187        force: null // Choose 'ios', 'android' or 'windows'. Don't do a browser check, just always show this banner
188    }
189
190    $.smartbanner.Constructor = SmartBanner
191
192}(window.jQuery);

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.