diff --git a/assets/prefer-iitc.psd b/assets/prefer-iitc.psd new file mode 100644 index 00000000..bf0e1424 Binary files /dev/null and b/assets/prefer-iitc.psd differ diff --git a/code/artifact.js b/code/artifact.js index cd8b118d..d52abc72 100644 --- a/code/artifact.js +++ b/code/artifact.js @@ -247,7 +247,10 @@ window.artifact.showArtifactList = function() { } if (data[type].fragments) { - row += 'Shard: #'+data[type].fragments.join(', #')+' '; + if (data[type].target) { + row += '
'; + } + row += 'Shard: #'+data[type].fragments.join(', #')+' '; sortVal = Math.min.apply(null, data[type].fragments); // use min shard number at portal as sort key } diff --git a/code/chat.js b/code/chat.js index 2bcf5f79..50cb8fec 100644 --- a/code/chat.js +++ b/code/chat.js @@ -228,12 +228,12 @@ window.chat.renderCompact = function(oldMsgsWereAdded) { $.each(chat._public.data, function(guid, entry) { // skip player msgs if(!entry[1]) return true; - var pguid = entry[3]; + var nick = entry[3]; // ignore if player has newer data - if(data[pguid] && data[pguid][0] > entry[0]) return true; - data[pguid] = entry; + if(data[nick] && data[nick][0] > entry[0]) return true; + data[nick] = entry; }); - // data keys are now player guids instead of message guids. However, + // data keys are now player nicks instead of message guids. However, // it is all the same to renderData. chat.renderData(data, 'chatcompact', oldMsgsWereAdded); } @@ -350,7 +350,7 @@ window.chat.writeDataToHash = function(newData, storageHash, isPublicChannel, is // format: timestamp, autogenerated, HTML message - storageHash.data[json[0]] = [json[1], auto, chat.renderMsg(msg, nick, time, team, msgToPlayer, systemNarrowcast)]; + storageHash.data[json[0]] = [json[1], auto, chat.renderMsg(msg, nick, time, team, msgToPlayer, systemNarrowcast), nick]; }); } diff --git a/code/hooks.js b/code/hooks.js index 60eefe45..1de476f3 100644 --- a/code/hooks.js +++ b/code/hooks.js @@ -89,6 +89,7 @@ window.runHooks = function(event, data) { window.addHook = function(event, callback) { if(VALID_HOOKS.indexOf(event) === -1) { console.error('addHook: Unknown event type: ' + event + ' - ignoring'); + debugger; return; } diff --git a/code/map_data_request.js b/code/map_data_request.js index 9c4f52be..1326d852 100644 --- a/code/map_data_request.js +++ b/code/map_data_request.js @@ -16,8 +16,9 @@ window.MapDataRequest = function() { // no more than this many requests in parallel. stock site seems to rely on browser limits (6, usually), sending - // all requests at once. using our own queue limit ensures that other requests (e.g. chat) don't get postponed for too long - this.MAX_REQUESTS = 6; + // many requests at once. + // using our own queue limit ensures that other requests (e.g. chat, portal details) don't get delayed + this.MAX_REQUESTS = 5; // no more than this many tiles in one request // as of 2013-11-11, or possibly the release before that, the stock site was changed to only request four tiles at a time @@ -28,7 +29,7 @@ window.MapDataRequest = function() { this.MIN_TILES_PER_REQUEST = 4; // number of times to retry a tile after a 'bad' error (i.e. not a timeout) - this.MAX_TILE_RETRIES = 1; + this.MAX_TILE_RETRIES = 2; // refresh timers this.MOVE_REFRESH = 1; //time, after a map move (pan/zoom) before starting the refresh processing diff --git a/code/portal_detail_display.js b/code/portal_detail_display.js index 9c26ea59..53a54b99 100644 --- a/code/portal_detail_display.js +++ b/code/portal_detail_display.js @@ -109,7 +109,7 @@ window.renderPortalDetails = function(guid) { } else { // non-android - a permalink for the portal - var permaHtml = $('
').html( $('').attr({href:permalinkUrl, target:'_blank', title:'Create a URL link to this portal'}).text('Portal link') ).html(); + var permaHtml = $('
').html( $('').attr({href:permalinkUrl, title:'Create a URL link to this portal'}).text('Portal link') ).html(); linkDetails.push ( '' ); // and a map link popup dialog diff --git a/code/portal_info.js b/code/portal_info.js index d8be6198..cd2af05e 100644 --- a/code/portal_info.js +++ b/code/portal_info.js @@ -68,22 +68,23 @@ window.getLinkAmpRangeBoost = function(d) { // (at the time of writing, only rare link amps have been seen in the wild, so there's a little guesswork at how // the stats work and combine - jon 2013-06-26) - // link amps scale: first is full, second half, the last two a quarter - var scale = [1.0, 0.5, 0.25, 0.25]; + // link amps scale: first is full, second a quarter, the last two an eigth + var scale = [1.0, 0.25, 0.125, 0.125]; - var boost = 1.0; // initial boost is 1.0 (i.e. no boost over standard range) + var boost = 0.0; // initial boost is 0.0 (i.e. no boost over standard range) var count = 0; - $.each(d.portalV2.linkedModArray, function(ind, mod) { - if(mod && mod.type === 'LINK_AMPLIFIER' && mod.stats && mod.stats.LINK_RANGE_MULTIPLIER) { - // link amp stat LINK_RANGE_MULTIPLIER is 2000 for rare, and gives 2x boost to the range - var baseMultiplier = mod.stats.LINK_RANGE_MULTIPLIER/1000; - boost += (baseMultiplier-1)*scale[count]; - count++; - } + var linkAmps = getPortalModsByType(d, 'LINK_AMPLIFIER'); + + $.each(linkAmps, function(ind, mod) { + // link amp stat LINK_RANGE_MULTIPLIER is 2000 for rare, and gives 2x boost to the range + // and very-rare is 7000 and gives 7x the range + var baseMultiplier = mod.stats.LINK_RANGE_MULTIPLIER/1000; + boost += baseMultiplier*scale[count]; + count++; }); - return boost; + return (count > 0) ? boost : 1.0; } diff --git a/external/L.Geodesic.js b/external/L.Geodesic.js index 8a6ef59e..6313db95 100644 --- a/external/L.Geodesic.js +++ b/external/L.Geodesic.js @@ -58,19 +58,23 @@ Modified by qnstie 2013-07-17 to maintain compatibility with Leaflet.draw // loop ends before 'segments' is reached - we don't add the very last point here but outside the loop // (this was to fix a bug - https://github.com/jonatkins/ingress-intel-total-conversion/issues/471 // rounding errors? maths bug? not sure - but it solves the issue! and is a slight optimisation) - for (i = 1; i < segments; i++) { - // http://williams.best.vwh.net/avform.htm#Intermediate - // modified to handle longitude above +-180 degrees - f = i / segments; - A = Math.sin((1-f)*d) / Math.sin(d); - B = Math.sin(f*d) / Math.sin(d); - x = A * Math.cos(lat1) * Math.cos(0) + B * Math.cos(lat2) * Math.cos(dLng); - y = A * Math.cos(lat1) * Math.sin(0) + B * Math.cos(lat2) * Math.sin(dLng); - z = A * Math.sin(lat1) + B * Math.sin(lat2); - fLat = r2d * Math.atan2(z, Math.sqrt(Math.pow(x, 2) + Math.pow(y, 2))); - fLng = r2d * (Math.atan2(y, x)+lng1); + // UPDATE: there still seem to be rounding errors on relatively short links - but only on mobile. + // let's only add intermediate points if there's two or more + if (segments >= 3) { + for (i = 1; i < segments; i++) { + // http://williams.best.vwh.net/avform.htm#Intermediate + // modified to handle longitude above +-180 degrees + f = i / segments; + A = Math.sin((1-f)*d) / Math.sin(d); + B = Math.sin(f*d) / Math.sin(d); + x = A * Math.cos(lat1) * Math.cos(0) + B * Math.cos(lat2) * Math.cos(dLng); + y = A * Math.cos(lat1) * Math.sin(0) + B * Math.cos(lat2) * Math.sin(dLng); + z = A * Math.sin(lat1) + B * Math.sin(lat2); + fLat = r2d * Math.atan2(z, Math.sqrt(Math.pow(x, 2) + Math.pow(y, 2))); + fLng = r2d * (Math.atan2(y, x)+lng1); - convertedPoints.push(L.latLng([fLat, fLng])); + convertedPoints.push(L.latLng([fLat, fLng])); + } } // push the final point unmodified convertedPoints.push(L.latLng(endLatlng)); diff --git a/mobile/res/drawable-hdpi/ic_action_data_usage.png b/mobile/res/drawable-hdpi/ic_action_data_usage.png new file mode 100644 index 00000000..f0f83a02 Binary files /dev/null and b/mobile/res/drawable-hdpi/ic_action_data_usage.png differ diff --git a/mobile/res/drawable-mdpi/ic_action_data_usage.png b/mobile/res/drawable-mdpi/ic_action_data_usage.png new file mode 100644 index 00000000..02ebf1eb Binary files /dev/null and b/mobile/res/drawable-mdpi/ic_action_data_usage.png differ diff --git a/mobile/res/drawable-xhdpi/ic_action_data_usage.png b/mobile/res/drawable-xhdpi/ic_action_data_usage.png new file mode 100644 index 00000000..487f4f82 Binary files /dev/null and b/mobile/res/drawable-xhdpi/ic_action_data_usage.png differ diff --git a/mobile/res/drawable-xxhdpi/ic_action_data_usage.png b/mobile/res/drawable-xxhdpi/ic_action_data_usage.png new file mode 100644 index 00000000..76631a4d Binary files /dev/null and b/mobile/res/drawable-xxhdpi/ic_action_data_usage.png differ diff --git a/mobile/src/com/cradle/iitc_mobile/IITC_NavigationHelper.java b/mobile/src/com/cradle/iitc_mobile/IITC_NavigationHelper.java index 79ce1b9f..62254373 100644 --- a/mobile/src/com/cradle/iitc_mobile/IITC_NavigationHelper.java +++ b/mobile/src/com/cradle/iitc_mobile/IITC_NavigationHelper.java @@ -6,6 +6,7 @@ import android.content.DialogInterface; import android.content.DialogInterface.OnClickListener; import android.content.DialogInterface.OnDismissListener; import android.content.SharedPreferences; +import android.content.res.Resources; import android.os.Bundle; import android.os.Handler; import android.preference.PreferenceManager; @@ -166,7 +167,7 @@ public class IITC_NavigationHelper extends ActionBarDrawerToggle implements OnIt } } - if (mDrawerLayout.isDrawerOpen(mDrawerLeft)) { + if (mDrawerLayout.isDrawerOpen(mDrawerLeft) || mPane == Pane.MAP) { mActionBar.setTitle(mIitc.getString(R.string.app_name)); } else { mActionBar.setTitle(mPane.label); @@ -184,7 +185,16 @@ public class IITC_NavigationHelper extends ActionBarDrawerToggle implements OnIt public void addPane(String name, String label, String icon) { showNotice(NOTICE_PANES); - int resId = mIitc.getResources().getIdentifier(icon, "drawable", mIitc.getPackageName()); + Resources res = mIitc.getResources(); + String packageName = res.getResourcePackageName(R.string.app_name); + /* + * since the package name is overridden in test builds + * we can't use context.getPackageName() to get the package name + * because the resources were processed before the package name was finally updated. + * so we have to retrieve the package name of another resource with Resources.getResourcePackageName() + * see http://www.piwai.info/renaming-android-manifest-package/ + */ + int resId = mIitc.getResources().getIdentifier(icon, "drawable", packageName); mNavigationAdapter.add(new Pane(name, label, resId)); } @@ -341,7 +351,7 @@ public class IITC_NavigationHelper extends ActionBarDrawerToggle implements OnIt public static final Pane FACTION = new Pane("faction", "Faction", R.drawable.ic_action_cc_bcc); public static final Pane FULL = new Pane("full", "Full", R.drawable.ic_action_view_as_list); public static final Pane INFO = new Pane("info", "Info", R.drawable.ic_action_about); - public static final Pane MAP = new Pane("map", "IITC Mobile", R.drawable.ic_action_map); + public static final Pane MAP = new Pane("map", "Map", R.drawable.ic_action_map); public static final Pane PUBLIC = new Pane("public", "Public", R.drawable.ic_action_group); private int icon; diff --git a/plugins/draw-resonators.user.js b/plugins/draw-resonators.user.js index 755b6d46..9111ede7 100644 --- a/plugins/draw-resonators.user.js +++ b/plugins/draw-resonators.user.js @@ -38,7 +38,7 @@ window.plugin.drawResonators.portalSelected = function(data) { } } -window.plugin.drawResonators.portalDetailsLoaded = function(data) { +window.plugin.drawResonators.portalDetailLoaded = function(data) { // the detailed data for a portal was just loaded - if this is the selected portal, draw them if (data.guid == window.selectedPortal) { @@ -117,6 +117,13 @@ window.plugin.drawResonators.zoomListener = function() { ctrl.addClass('disabled').attr('title', 'Zoom in to show those.'); } else { ctrl.removeClass('disabled').attr('title', 'Select a portal to draw resos'); + window.plugin.drawResonators.levelLayerGroup.clearLayers(); + if (window.selectedPortal) { + var details = portalDetail.get(window.selectedPortal); + if (details) { + window.plugin.drawResonators.drawData(details); + } + } }; } @@ -127,7 +134,7 @@ var setup = function() { window.addLayerGroup('Resonators', window.plugin.drawResonators.levelLayerGroup, true); window.addHook('portalSelected', window.plugin.drawResonators.portalSelected); - window.addHook('portalDetailsLoaded', window.plugin.drawResonators.portalDetailsLoaded); + window.addHook('portalDetailLoaded', window.plugin.drawResonators.portalDetailLoaded); window.map.on('zoomend', function() { window.plugin.drawResonators.zoomListener(); diff --git a/plugins/iitc-ditigal-bumper-sticker.user.js b/plugins/iitc-ditigal-bumper-sticker.user.js new file mode 100644 index 00000000..d2ceb91d --- /dev/null +++ b/plugins/iitc-ditigal-bumper-sticker.user.js @@ -0,0 +1,26 @@ +// ==UserScript== +// @id iitc-digital-bumper-sticker +// @name IITC Digital Bumper Sticker +// @category Stock +// @version 0.1.0.@@DATETIMEVERSION@@ +// @namespace https://github.com/jonatkins/ingress-intel-total-conversion +// @updateURL @@UPDATEURL@@ +// @downloadURL @@DOWNLOADURL@@ +// @description [@@BUILDNAME@@-@@BUILDDATE@@] Adds a "I'd rather be using IITC" logo to the standard intel map. +// @include https://www.ingress.com/intel* +// @include http://www.ingress.com/intel* +// @match https://www.ingress.com/intel* +// @match http://www.ingress.com/intel* +// @grant none +// ==/UserScript== + +var logoDiv = document.createElement('div'); +logoDiv.setAttribute('style', "position: fixed; left: 20px; top: 130px; z-index: auto; pointer-events: none;"); + +var img = document.createElement('img'); +img.setAttribute('src', 'http://iitc.jonatkins.com/assets/img/prefer-iitc-200.png'); + +logoDiv.appendChild(img); + +var targetContainer = document.getElementById('dashboard_container'); +targetContainer.appendChild(logoDiv); diff --git a/plugins/portal-counts.user.js b/plugins/portal-counts.user.js index f1deeaef..60a41ec9 100644 --- a/plugins/portal-counts.user.js +++ b/plugins/portal-counts.user.js @@ -2,7 +2,7 @@ // @id iitc-plugin-portals-count@yenky // @name IITC plugin: Show total counts of portals // @category Info -// @version 0.0.9.@@DATETIMEVERSION@@ +// @version 0.1.0.@@DATETIMEVERSION@@ // @namespace https://github.com/jonatkins/ingress-intel-total-conversion // @updateURL @@UPDATEURL@@ // @downloadURL @@DOWNLOADURL@@ @@ -19,95 +19,303 @@ // PLUGIN START //////////////////////////////////////////////////////// /* whatsnew -* 0.0.8 : use dialog() instead of alert() -* 0.0.6 : ignoring outside bounds portals (even if close to) -* 0.0.5 : changed table layout, added some colors -* 0.0.4 : reverse show order of portals, using MAX_PORTAL_LEVEL now for array, changed table layout to be more compact, cleaned up code -* 0.0.3 : fixed incorrect rounded portal levels, adjusted viewport -* 0.0.2 : fixed counts to be reset after scrolling -* 0.0.1 : initial release, show count of portals -* todo : -*/ +* 0.1.0 : display graphs +* 0.0.10 : show in nav drawer on mobile devices +* 0.0.9 : fix for new intel map +* 0.0.8 : use dialog() instead of alert() +* 0.0.6 : ignoring outside bounds portals (even if close to) +* 0.0.5 : changed table layout, added some colors +* 0.0.4 : reverse show order of portals, using MAX_PORTAL_LEVEL now for array, changed table layout to be more compact, cleaned up code +* 0.0.3 : fixed incorrect rounded portal levels, adjusted viewport +* 0.0.2 : fixed counts to be reset after scrolling +* 0.0.1 : initial release, show count of portals +*/ // use own namespace for plugin -window.plugin.portalcounts = function() {}; +window.plugin.portalcounts = { + BAR_TOP: 20, + BAR_HEIGHT: 180, + BAR_WIDTH: 25, + BAR_PADDING: 5, + RADIUS_INNER: 70, + RADIUS_OUTER: 100, + CENTER_X: 200, + CENTER_Y: 100, +}; //count portals for each level available on the map -window.plugin.portalcounts.getPortals = function(){ +window.plugin.portalcounts.getPortals = function (){ //console.log('** getPortals'); - var retval=false; + var self = window.plugin.portalcounts; var displayBounds = map.getBounds(); - window.plugin.portalcounts.enlP = 0; - window.plugin.portalcounts.resP = 0; - window.plugin.portalcounts.neuP = 0; - - window.plugin.portalcounts.PortalsEnl = new Array(); - window.plugin.portalcounts.PortalsRes = new Array(); + self.enlP = 0; + self.resP = 0; + self.neuP = 0; + + self.PortalsEnl = new Array(); + self.PortalsRes = new Array(); for(var level = window.MAX_PORTAL_LEVEL; level > 0; level--){ - window.plugin.portalcounts.PortalsEnl[level] = 0; - window.plugin.portalcounts.PortalsRes[level] = 0; + self.PortalsEnl[level] = 0; + self.PortalsRes[level] = 0; } - + $.each(window.portals, function(i, portal) { - retval=true; var level = portal.options.level; var team = portal.options.team; // just count portals in viewport if(!displayBounds.contains(portal.getLatLng())) return true; switch (team){ case 1 : - window.plugin.portalcounts.resP++; - window.plugin.portalcounts.PortalsRes[level]++; + self.resP++; + self.PortalsRes[level]++; break; case 2 : - window.plugin.portalcounts.enlP++; - window.plugin.portalcounts.PortalsEnl[level]++; + self.enlP++; + self.PortalsEnl[level]++; break; default: - window.plugin.portalcounts.neuP++; + self.neuP++; break; } }); - + //get portals informations from IITC var minlvl = getMinPortalLevel(); + var total = self.neuP + self.enlP + self.resP; - var counts = ''; - if(retval) { - counts += ''; //'+window.plugin.portalcounts.enlP+' Portal(s)'; + var counts = ''; + if(total > 0) { + counts += '
EnlightenedResistance
'; //'+self.enlP+' Portal(s)'; for(var level = window.MAX_PORTAL_LEVEL; level > 0; level--){ counts += ''; if(minlvl > level) counts += ''; else - counts += ''; + counts += ''; counts += ''; } - counts += ''; + counts += ''; counts += ''; + counts += self.neuP; + counts += '
EnlightenedResistance
Level '+level+'zoom in to see portals in this level'+window.plugin.portalcounts.PortalsEnl[level]+''+window.plugin.portalcounts.PortalsRes[level]+''+self.PortalsEnl[level]+''+self.PortalsRes[level]+'
Total:'+window.plugin.portalcounts.enlP+''+window.plugin.portalcounts.resP+'
Total:'+self.enlP+''+self.resP+'
Neutral:'; if(minlvl > 0) counts += 'zoom in to see unclaimed portals'; else - counts += window.plugin.portalcounts.neuP; - counts += '
'; + var svg = $('').css("margin-top", 10); + + var all = self.PortalsRes.map(function(val,i){return val+self.PortalsEnl[i]}); + all[0] = self.neuP; + + // bar graphs + self.makeBar(self.PortalsEnl, "Enl", COLORS[2], 0 ).appendTo(svg); + self.makeBar(all , "All", "#FFFFFF", 1*(self.BAR_WIDTH + self.BAR_PADDING)).appendTo(svg); + self.makeBar(self.PortalsRes, "Res", COLORS[1], 2*(self.BAR_WIDTH + self.BAR_PADDING)).appendTo(svg); + + // pie graph + var g = $("") + .attr("transform", self.format("translate(%s,%s)", self.CENTER_X, self.CENTER_Y)) + .appendTo(svg); + + // inner parts - factions + self.makePie(0, self.resP/total, COLORS[1]).appendTo(g); + self.makePie(self.resP/total, (self.neuP + self.resP)/total, COLORS[0]).appendTo(g); + self.makePie((self.neuP + self.resP)/total, 1, COLORS[2]).appendTo(g); + + // outer part - levels + var angle = 0; + for(var i=self.PortalsRes.length-1;i>=0;i--) { + if(!self.PortalsRes[i]) + continue; + + var diff = self.PortalsRes[i] / total; + self.makeRing(angle, angle+diff, COLORS_LVL[i]).appendTo(g); + angle += diff; + } + + var diff = self.neuP / total; + self.makeRing(angle, angle+diff, COLORS_LVL[0]).appendTo(g); + angle += diff; + + for(var i=0;i") + .attr({ + x1: self.resP") + .attr({ + x1: self.resP").append(svg).html(); } else - counts += '
No Portals in range!
'; - counts += ''; + counts += '

No Portals in range!

'; + var total = self.enlP + self.resP + self.neuP; + var title = total + ' ' + (total == 1 ? 'portal' : 'portals'); - var total = window.plugin.portalcounts.enlP + window.plugin.portalcounts.resP + window.plugin.portalcounts.neuP; - dialog({ - html: '
' + counts + '
', - title: 'Portal counts: ' + total + ' ' + (total == 1 ? 'portal' : 'portals'), - }); + if(typeof android !== 'undefined' && android && android.addPane) { + $('
' + + '
' + title + '
' + + counts + + '
').appendTo(document.body); + } else { + dialog({ + html: '
' + counts + '
', + title: 'Portal counts: ' + title, + width: 'auto' + }); + } } +window.plugin.portalcounts.makeBar = function(portals, text, color, shift) { + var self = window.plugin.portalcounts; + var g = $("").attr("transform", "translate("+shift+",0)"); + var sum = portals.reduce(function(a,b){ return a+b }); + var top = self.BAR_TOP; + + if(sum != 0) { + for(var i=portals.length-1;i>=0;i--) { + if(!portals[i]) + continue; + var height = self.BAR_HEIGHT * portals[i] / sum; + $("") + .attr({ + x: 0, + y: top, + width: self.BAR_WIDTH, + height: height, + fill: COLORS_LVL[i] + }) + .appendTo(g); + top += height; + } + } + + $('') + .html(text) + .attr({ + x: self.BAR_WIDTH * 0.5, + y: self.BAR_TOP * 0.75, + fill: color, + "text-anchor": "middle" + }) + .appendTo(g); + + return g; +}; + +window.plugin.portalcounts.makePie = function(startAngle, endAngle, color) { + var self = window.plugin.portalcounts; + var large_arc = (endAngle - startAngle) > 0.5 ? 1 : 0; + + startAngle = 0.5 - startAngle; + endAngle = 0.5 - endAngle; + + var p1x = Math.sin(startAngle * 2 * Math.PI) * self.RADIUS_INNER; + var p1y = Math.cos(startAngle * 2 * Math.PI) * self.RADIUS_INNER; + var p2x = Math.sin(endAngle * 2 * Math.PI) * self.RADIUS_INNER; + var p2y = Math.cos(endAngle * 2 * Math.PI) * self.RADIUS_INNER; + + // for a full circle, both coordinates would be identical, so no circle would be drawn + if(startAngle == 0.5 && endAngle == -0.5) + p2x -= 1E-5; + + return $("") + .attr({ + fill: color, + d: self.format("M %s,%s A %s,%s 0 %s 1 %s,%s L 0,0 z", p1x,p1y, self.RADIUS_INNER,self.RADIUS_INNER, large_arc, p2x,p2y) + }); +}; + +window.plugin.portalcounts.makeRing = function(startAngle, endAngle, color) { + var self = window.plugin.portalcounts; + var large_arc = (endAngle - startAngle) > 0.5 ? 1 : 0; + + startAngle = 0.5 - startAngle; + endAngle = 0.5 - endAngle; + + var p1x = Math.sin(startAngle * 2 * Math.PI) * self.RADIUS_OUTER; + var p1y = Math.cos(startAngle * 2 * Math.PI) * self.RADIUS_OUTER; + var p2x = Math.sin(endAngle * 2 * Math.PI) * self.RADIUS_OUTER; + var p2y = Math.cos(endAngle * 2 * Math.PI) * self.RADIUS_OUTER; + var p3x = Math.sin(endAngle * 2 * Math.PI) * self.RADIUS_INNER; + var p3y = Math.cos(endAngle * 2 * Math.PI) * self.RADIUS_INNER; + var p4x = Math.sin(startAngle * 2 * Math.PI) * self.RADIUS_INNER; + var p4y = Math.cos(startAngle * 2 * Math.PI) * self.RADIUS_INNER; + + // for a full circle, both coordinates would be identical, so no circle would be drawn + if(startAngle == 0.5 && endAngle == -0.5) { + p2x -= 1E-5; + p3x -= 1E-5; + } + + return $("") + .attr({ + fill: color, + d: self.format("M %s,%s ", p1x, p1y) + + self.format("A %s,%s 0 %s 1 %s,%s ", self.RADIUS_OUTER,self.RADIUS_OUTER, large_arc, p2x,p2y) + + self.format("L %s,%s ", p3x,p3y) + + self.format("A %s,%s 0 %s 0 %s,%s ", self.RADIUS_INNER,self.RADIUS_INNER, large_arc, p4x,p4y) + + "Z" + }); +}; + +window.plugin.portalcounts.format = function(str) { + var re = /%s/; + for(var i = 1; i < arguments.length; i++) { + str = str.replace(re, arguments[i]); + } + return str; +} + +window.plugin.portalcounts.onPaneChanged = function(pane) { + if(pane == "plugin-portalcounts") + window.plugin.portalcounts.getPortals(); + else + $("#portalcounts").remove() +}; + var setup = function() { - $('#toolbox').append('
Portal counts'); - $('head').append(''); diff --git a/plugins/portals-list.user.js b/plugins/portals-list.user.js index 6b173449..50e9c8b3 100644 --- a/plugins/portals-list.user.js +++ b/plugins/portals-list.user.js @@ -45,10 +45,11 @@ window.plugin.portalslist = function() {}; window.plugin.portalslist.listPortals = []; -window.plugin.portalslist.sortOrder=-1; +window.plugin.portalslist.sortBy = 'level'; +window.plugin.portalslist.sortOrder = -1; window.plugin.portalslist.enlP = 0; window.plugin.portalslist.resP = 0; -window.plugin.portalslist.filter=0; +window.plugin.portalslist.filter = 0; //fill the listPortals array with portals avaliable on the map (level filtered portals will not appear in the table) window.plugin.portalslist.getPortals = function() { @@ -64,16 +65,14 @@ window.plugin.portalslist.getPortals = function() { retval=true; var d = portal.options.data; - var teamN = window.TEAM_NONE; + var teamN = portal.options.team; - switch (d.team){ - case 'RESISTANCE' : + switch (teamN) { + case TEAM_RES: window.plugin.portalslist.resP++; - teamN = window.TEAM_RES break; - case 'ENLIGHTENED' : + case TEAM_ENL: window.plugin.portalslist.enlP++; - teamN = window.TEAM_ENL; break; } var l = window.getPortalLinks(i); @@ -84,6 +83,7 @@ window.plugin.portalslist.getPortals = function() { 'guid': i, 'teamN': teamN, 'name': d.title, + 'nameLower': d.title.toLowerCase(), 'team': d.team, 'level': portal.options.level, 'health': d.health, @@ -102,12 +102,14 @@ window.plugin.portalslist.getPortals = function() { window.plugin.portalslist.displayPL = function() { var html = ''; - window.plugin.portalslist.sortOrder=-1; + window.plugin.portalslist.sortBy = 'level'; + window.plugin.portalslist.sortOrder = -1; window.plugin.portalslist.enlP = 0; window.plugin.portalslist.resP = 0; + window.plugin.portalslist.filter = 0; if (window.plugin.portalslist.getPortals()) { - html += window.plugin.portalslist.portalTable('level', window.plugin.portalslist.sortOrder,window.plugin.portalslist.filter); + html += window.plugin.portalslist.portalTable(window.plugin.portalslist.sortBy, window.plugin.portalslist.sortOrder,window.plugin.portalslist.filter); } else { html = '
Nothing to show!
'; }; @@ -123,84 +125,94 @@ window.plugin.portalslist.displayPL = function() { width: 700 }); } - - //run the name resolving process - //resolvePlayerNames(); } window.plugin.portalslist.portalTable = function(sortBy, sortOrder, filter) { - // sortOrder <0 ==> desc, >0 ==> asc, i use sortOrder * -1 to change the state - window.plugin.portalslist.filter=filter; + // save the sortBy/sortOrder/filter + window.plugin.portalslist.sortBy = sortBy; + window.plugin.portalslist.sortOrder = sortOrder; + window.plugin.portalslist.filter = filter; + var portals=window.plugin.portalslist.listPortals; //Array sort window.plugin.portalslist.listPortals.sort(function(a, b) { var retVal = 0; - switch (sortBy) { - case 'names': - retVal = a.name.toLowerCase() < b.name.toLowerCase() ? -1 : 1; - break; - default: - retVal = b[sortBy] - a[sortBy]; - break; + + var aComp = a[sortBy]; + var bComp = b[sortBy]; + + if (aComp < bComp) { + retVal = -1; + } else if (aComp > bComp) { + retVal = 1; + } else { + // equal - compare GUIDs to ensure consistant (but arbitary) order + retVal = a.guid < b.guid ? -1 : 1; } - if (sortOrder > 0) retVal = -retVal; //thx @jonatkins + + // sortOrder is 1 (normal) or -1 (reversed) + retVal = retVal * sortOrder; return retVal; }); - var sort = window.plugin.portalslist.portalTableSort; + var sortAttr = window.plugin.portalslist.portalTableHeaderSortAttr; var html = window.plugin.portalslist.stats(); html += '' - + '' - + '' - + '' - + '' - + '' - + '' - + '' + + '' + + '' + + '' + + '' + + '' + + '' + + '' + + '' + + '' + var rowNum = 1; $.each(portals, function(ind, portal) { if (filter === TEAM_NONE || filter === portal.teamN) { + html += '' - + '' - + '' - + ''; + + '' + + '' + + '' + + ''; html += '' + '' - + '' - + ''; + + '' + + ''; html+= ''; + + rowNum++; } }); html += '
PortalLevelTeamHealthResonator CountLink CountField Count
#Portal NameLevelTeamHealthResonatorsLinksFields
' + window.plugin.portalslist.getPortalLink(portal, portal.guid) + '' + portal.level + '' + portal.team + ''+rowNum+'' + window.plugin.portalslist.getPortalLink(portal, portal.guid) + '' + portal.level + '' + portal.team.substr(0,3) + '' + portal.health + '' + portal.resCount + '' + portal.linkCount + '' + portal.fieldCount + '' + (portal.linkCount?portal.linkCount:'-') + '' + (portal.fieldCount?portal.fieldCount:'-') + '
'; html += '
Click on portals table headers to sort by that column. ' - + 'Click on All Portals, Resistance Portals, Enlightened Portals to filter
' - + 'Thanks to @vita10gy & @xelio for their IITC plugins who inspired me. A @teo96 production. Vive la Résistance !
'; + + 'Click on All Portals, Resistance Portals, Enlightened Portals to filter
'; - window.plugin.portalslist.sortOrder = window.plugin.portalslist.sortOrder*-1; return html; } window.plugin.portalslist.stats = function(sortBy) { var html = '' - + '' - + '' - + '' + + '' + + '' + + '' + '' + '
All Portals : (click to filter)' + window.plugin.portalslist.listPortals.length + 'Resistance Portals : ' + window.plugin.portalslist.resP +' (' + Math.floor(window.plugin.portalslist.resP/window.plugin.portalslist.listPortals.length*100) + '%)Enlightened Portals : '+ window.plugin.portalslist.enlP +' (' + Math.floor(window.plugin.portalslist.enlP/window.plugin.portalslist.listPortals.length*100) + '%)All Portals : (click to filter)' + window.plugin.portalslist.listPortals.length + 'Resistance Portals : ' + window.plugin.portalslist.resP +' (' + Math.floor(window.plugin.portalslist.resP/window.plugin.portalslist.listPortals.length*100) + '%)Enlightened Portals : '+ window.plugin.portalslist.enlP +' (' + Math.floor(window.plugin.portalslist.enlP/window.plugin.portalslist.listPortals.length*100) + '%)
'; return html; } // A little helper function so the above isn't so messy -window.plugin.portalslist.portalTableSort = function(name, by) { - var retVal = 'data-sort="' + name + '"'; - if(name === by) { - retVal += ' class="sorted"'; - } +window.plugin.portalslist.portalTableHeaderSortAttr = function(name, by, defOrder, extraClass) { + // data-sort attr: used by jquery .data('sort') below + var retVal = 'data-sort="'+name+'" data-defaultorder="'+defOrder+'" class="'+(extraClass?extraClass+' ':'')+'sortable'+(name==by?' sorted':'')+'"'; + return retVal; }; @@ -224,7 +236,7 @@ window.plugin.portalslist.getPortalLink = function(portal,guid) { onClick: jsSingleClick, onDblClick: jsDoubleClick })[0].outerHTML; - var div = '
'+a+'
'; + var div = '
'+a+'
'; return div; } @@ -252,28 +264,33 @@ var setup = function() { '#portalslist table tr.neutral td { background-color: #000000; }' + '#portalslist table th { text-align: center;}' + '#portalslist table td { text-align: center;}' + - '#portalslist table td:nth-child(1) { text-align: left;}' + - '#portalslist table th { cursor:pointer;}' + - '#portalslist table th:nth-child(1) { text-align: left;}' + - '#portalslist table th.sorted { color:#FFCE00; }' + + '#portalslist table td.portalTitle { text-align: left;}' + + '#portalslist table th.sortable { cursor:pointer;}' + + '#portalslist table th.portalTitle { text-align: left;}' + + '#portalslist .sorted { color:#FFCE00; }' + '#portalslist .filterAll { margin-top: 10px;}' + '#portalslist .filterRes { margin-top: 10px; background-color: #005684 }' + '#portalslist .filterEnl { margin-top: 10px; background-color: #017f01 }' + '#portalslist .disclaimer { margin-top: 10px; font-size:10px; }' + - '#portalslist .portalTitle { display: inline-block; width: 160px !important; min-width: 160px !important; max-width: 160px !important; overflow: hidden; white-space: nowrap; text-overflow: ellipsis; }' + + '#portalslist .portalTitleTruncate { display: inline-block; width: 240px !important; min-width: 240px !important; max-width: 160px !important; overflow: hidden; white-space: nowrap; text-overflow: ellipsis; }' + ''); + // Setup sorting - $(document).on('click.portalslist', '#portalslist table th', function() { - $('#portalslist').html(window.plugin.portalslist.portalTable($(this).data('sort'),window.plugin.portalslist.sortOrder,window.plugin.portalslist.filter)); + $(document).on('click.portalslist', '#portalslist table th.sortable', function() { + var sortBy = $(this).data('sort'); + // if this is the currently selected column, toggle the sort order - otherwise use the columns default sort order + var sortOrder = sortBy == window.plugin.portalslist.sortBy ? window.plugin.portalslist.sortOrder*-1 : parseInt($(this).data('defaultorder')); + $('#portalslist').html(window.plugin.portalslist.portalTable(sortBy,sortOrder,window.plugin.portalslist.filter)); }); + $(document).on('click.portalslist', '#portalslist .filterAll', function() { - $('#portalslist').html(window.plugin.portalslist.portalTable($(this).data('sort'),window.plugin.portalslist.sortOrder,0)); + $('#portalslist').html(window.plugin.portalslist.portalTable(window.plugin.portalslist.sortBy,window.plugin.portalslist.sortOrder,0)); }); $(document).on('click.portalslist', '#portalslist .filterRes', function() { - $('#portalslist').html(window.plugin.portalslist.portalTable($(this).data('sort'),window.plugin.portalslist.sortOrder,1)); + $('#portalslist').html(window.plugin.portalslist.portalTable(window.plugin.portalslist.sortBy,window.plugin.portalslist.sortOrder,1)); }); $(document).on('click.portalslist', '#portalslist .filterEnl', function() { - $('#portalslist').html(window.plugin.portalslist.portalTable($(this).data('sort'),window.plugin.portalslist.sortOrder,2)); + $('#portalslist').html(window.plugin.portalslist.portalTable(window.plugin.portalslist.sortBy,window.plugin.portalslist.sortOrder,2)); }); } diff --git a/website/assets/img/prefer-iitc-200.png b/website/assets/img/prefer-iitc-200.png new file mode 100644 index 00000000..3732c76f Binary files /dev/null and b/website/assets/img/prefer-iitc-200.png differ diff --git a/website/assets/img/prefer-iitc-205.png b/website/assets/img/prefer-iitc-205.png new file mode 100644 index 00000000..657ccb77 Binary files /dev/null and b/website/assets/img/prefer-iitc-205.png differ diff --git a/website/assets/img/prefer-iitc-256.png b/website/assets/img/prefer-iitc-256.png new file mode 100644 index 00000000..21b36023 Binary files /dev/null and b/website/assets/img/prefer-iitc-256.png differ diff --git a/website/assets/img/prefer-iitc-512.png b/website/assets/img/prefer-iitc-512.png new file mode 100644 index 00000000..5c6dc047 Binary files /dev/null and b/website/assets/img/prefer-iitc-512.png differ diff --git a/website/page/faq.php b/website/page/faq.php index 4d06b44a..72754750 100644 --- a/website/page/faq.php +++ b/website/page/faq.php @@ -9,7 +9,7 @@ Occasionally the Niantic servers give this misleading message - what it should u "Failed to check account status - please reload to try again". IITC will, in most cases, retry for you.

-Sometimes this is caused by server issues, and no ammount of reloading will fix it. Come back later and try again. +Sometimes this is caused by server issues, and no amount of reloading will fix it. Come back later and try again.

However, another reason for this message is your account being blocked/suspended by Niantic. There