mapshaper 0.6.2 → 0.6.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/mapshaper.js CHANGED
@@ -1,6 +1,6 @@
1
1
  (function () {
2
2
 
3
- var VERSION = "0.6.2";
3
+ var VERSION = "0.6.5";
4
4
 
5
5
 
6
6
  var utils = /*#__PURE__*/Object.freeze({
@@ -81,6 +81,7 @@
81
81
  get findValueByPct () { return findValueByPct; },
82
82
  get findValueByRank () { return findValueByRank; },
83
83
  get findMedian () { return findMedian; },
84
+ get findQuantile () { return findQuantile; },
84
85
  get mean () { return mean; },
85
86
  get format () { return format; },
86
87
  get formatter () { return formatter; },
@@ -832,18 +833,24 @@
832
833
  return arr[k];
833
834
  }
834
835
 
835
- //
836
- //
837
836
  function findMedian(arr) {
838
- var n = arr.length,
839
- rank = Math.floor(n / 2) + 1,
840
- median = findValueByRank(arr, rank);
841
- if ((n & 1) == 0) {
842
- median = (median + findValueByRank(arr, rank - 1)) / 2;
843
- }
844
- return median;
837
+ return findQuantile(arr, 0.5);
845
838
  }
846
839
 
840
+ function findQuantile(arr, k) {
841
+ var n = arr.length,
842
+ i1 = Math.floor((n - 1) * k),
843
+ i2 = Math.ceil((n - 1) * k);
844
+ if (i1 < 0 || i2 >= n) return NaN;
845
+ var v1 = findValueByRank(arr, i1 + 1);
846
+ if (i1 == i2) return v1;
847
+ var v2 = findValueByRank(arr, i2 + 1);
848
+ // use linear interpolation
849
+ var w1 = i2 / (n - 1) - k;
850
+ var w2 = k - i1 / (n - 1);
851
+ var v = (v1 * w1 + v2 * w2) * (n - 1);
852
+ return v;
853
+ }
847
854
 
848
855
  function mean(arr) {
849
856
  var count = 0,
@@ -10342,7 +10349,13 @@
10342
10349
  sum: captureNum,
10343
10350
  sums: capture,
10344
10351
  average: captureNum,
10352
+ mean: captureNum,
10345
10353
  median: captureNum,
10354
+ quantile: captureNum,
10355
+ iqr: captureNum,
10356
+ quartile1: captureNum,
10357
+ quartile2: captureNum,
10358
+ quartile3: captureNum,
10346
10359
  min: captureNum,
10347
10360
  max: captureNum,
10348
10361
  mode: capture,
@@ -10357,9 +10370,17 @@
10357
10370
  sum: wrap(utils.sum, 0),
10358
10371
  sums: wrap(sums),
10359
10372
  median: wrap(utils.findMedian),
10373
+ quantile: wrap2(utils.findQuantile),
10374
+ iqr: wrap(function(arr) {
10375
+ return utils.findQuantile(arr, 0.75) - utils.findQuantile(arr, 0.25);
10376
+ }),
10377
+ quartile1: wrap(function(arr) { return utils.findQuantile(arr, 0.25); }),
10378
+ quartile2: wrap(utils.findMedian),
10379
+ quartile3: wrap(function(arr) { return utils.findQuantile(arr, 0.75); }),
10360
10380
  min: wrap(min),
10361
10381
  max: wrap(max),
10362
10382
  average: wrap(utils.mean),
10383
+ mean: wrap(utils.mean),
10363
10384
  mode: wrap(getMode),
10364
10385
  collect: wrap(pass),
10365
10386
  first: wrap(pass),
@@ -10429,6 +10450,13 @@
10429
10450
  };
10430
10451
  }
10431
10452
 
10453
+ function wrap2(proc) {
10454
+ return function(arg1, arg2) {
10455
+ var c = colNo++;
10456
+ return rowNo > 0 ? proc(cols[c], arg2) : null;
10457
+ };
10458
+ }
10459
+
10432
10460
  function procAll() {
10433
10461
  for (var i=0; i<len; i++) {
10434
10462
  procRecord(i);
@@ -30912,7 +30940,7 @@ ${svg}
30912
30940
 
30913
30941
  var plasma = ramp(colors("0d088710078813078916078a19068c1b068d1d068e20068f2206902406912605912805922a05932c05942e05952f059631059733059735049837049938049a3a049a3c049b3e049c3f049c41049d43039e44039e46039f48039f4903a04b03a14c02a14e02a25002a25102a35302a35502a45601a45801a45901a55b01a55c01a65e01a66001a66100a76300a76400a76600a76700a86900a86a00a86c00a86e00a86f00a87100a87201a87401a87501a87701a87801a87a02a87b02a87d03a87e03a88004a88104a78305a78405a78606a68707a68808a68a09a58b0aa58d0ba58e0ca48f0da4910ea3920fa39410a29511a19613a19814a099159f9a169f9c179e9d189d9e199da01a9ca11b9ba21d9aa31e9aa51f99a62098a72197a82296aa2395ab2494ac2694ad2793ae2892b02991b12a90b22b8fb32c8eb42e8db52f8cb6308bb7318ab83289ba3388bb3488bc3587bd3786be3885bf3984c03a83c13b82c23c81c33d80c43e7fc5407ec6417dc7427cc8437bc9447aca457acb4679cc4778cc4977cd4a76ce4b75cf4c74d04d73d14e72d24f71d35171d45270d5536fd5546ed6556dd7566cd8576bd9586ada5a6ada5b69db5c68dc5d67dd5e66de5f65de6164df6263e06363e16462e26561e26660e3685fe4695ee56a5de56b5de66c5ce76e5be76f5ae87059e97158e97257ea7457eb7556eb7655ec7754ed7953ed7a52ee7b51ef7c51ef7e50f07f4ff0804ef1814df1834cf2844bf3854bf3874af48849f48948f58b47f58c46f68d45f68f44f79044f79143f79342f89441f89540f9973ff9983ef99a3efa9b3dfa9c3cfa9e3bfb9f3afba139fba238fca338fca537fca636fca835fca934fdab33fdac33fdae32fdaf31fdb130fdb22ffdb42ffdb52efeb72dfeb82cfeba2cfebb2bfebd2afebe2afec029fdc229fdc328fdc527fdc627fdc827fdca26fdcb26fccd25fcce25fcd025fcd225fbd324fbd524fbd724fad824fada24f9dc24f9dd25f8df25f8e125f7e225f7e425f6e626f6e826f5e926f5eb27f4ed27f3ee27f3f027f2f227f1f426f1f525f0f724f0f921"));
30914
30942
 
30915
- var lib = /*#__PURE__*/Object.freeze({
30943
+ var d3Scales = /*#__PURE__*/Object.freeze({
30916
30944
  __proto__: null,
30917
30945
  schemeCategory10: category10,
30918
30946
  schemeAccent: Accent,
@@ -31049,7 +31077,6 @@ ${svg}
31049
31077
  }
31050
31078
 
31051
31079
  function testLib() {
31052
- var lib = require('d3-scale-chromatic');
31053
31080
  schemes(index.categorical);
31054
31081
  schemes(index.sequential);
31055
31082
  schemes(index.diverging);
@@ -31059,7 +31086,7 @@ ${svg}
31059
31086
 
31060
31087
  function schemes(arr) {
31061
31088
  arr.forEach(function(name) {
31062
- if (!lib['scheme' + name]) {
31089
+ if (!d3Scales['scheme' + name]) {
31063
31090
  message('Warning: missing data for', name);
31064
31091
  }
31065
31092
  });
@@ -31067,7 +31094,7 @@ ${svg}
31067
31094
 
31068
31095
  function interpolators(arr) {
31069
31096
  arr.forEach(function(name) {
31070
- if (!lib['interpolate' + name]) {
31097
+ if (!d3Scales['interpolate' + name]) {
31071
31098
  message('Missing interpolator for', name);
31072
31099
  }
31073
31100
  });
@@ -31106,7 +31133,7 @@ ${svg}
31106
31133
  if (!isColorSchemeName(name)) {
31107
31134
  stop('Unknown color scheme name:', name);
31108
31135
  } else if (isCategoricalColorScheme(name)) {
31109
- colors = ramps[name] || require('d3-scale-chromatic')['scheme' + name];
31136
+ colors = ramps[name] || d3Scales['scheme' + name];
31110
31137
  } else {
31111
31138
  colors = getColorRamp(name, n);
31112
31139
  }
@@ -31140,9 +31167,8 @@ ${svg}
31140
31167
  function getColorRamp(name, n, stops) {
31141
31168
  initSchemes();
31142
31169
  name = standardName(name);
31143
- // var lib = require('d3-scale-chromatic');
31144
- var ramps = lib['scheme' + name];
31145
- var interpolate = lib['interpolate' + name];
31170
+ var ramps = d3Scales['scheme' + name];
31171
+ var interpolate = d3Scales['interpolate' + name];
31146
31172
  var ramp;
31147
31173
  if (!ramps && !interpolate) {
31148
31174
  stop('Unknown color scheme name:', name);
@@ -36778,6 +36804,7 @@ ${svg}
36778
36804
  } else {
36779
36805
  ctx = getNullLayerProxy(targets);
36780
36806
  }
36807
+ ctx.global = getStashedVar('defs') || {}; // TODO: remove duplication with mapshaper.expressions.mjs
36781
36808
  var exprOpts = Object.assign({returns: true}, opts);
36782
36809
  var func = compileExpressionToFunction(expr, exprOpts);
36783
36810
 
@@ -42056,6 +42083,13 @@ ${svg}
42056
42083
  inputObj = null;
42057
42084
  }
42058
42085
 
42086
+ if (commands.length === 0) {
42087
+ return callback(new UserError("No commands to run"));
42088
+ }
42089
+
42090
+ commands = runAndRemoveInfoCommands(commands);
42091
+ if (commands.length === 0) return done(null);
42092
+
42059
42093
  // add options to -i -o -join -clip -erase commands to bypass file i/o
42060
42094
  // TODO: find a less kludgy solution
42061
42095
  commands.forEach(function(cmd) {
@@ -42067,7 +42101,20 @@ ${svg}
42067
42101
  }
42068
42102
  });
42069
42103
 
42070
- runParsedCommands(commands, null, callback);
42104
+ var batches = divideImportCommand(commands);
42105
+ utils.reduceAsync(batches, null, nextGroup, done);
42106
+
42107
+ function nextGroup(prevJob, commands, next) {
42108
+ runParsedCommands(commands, new Job(), function(err, job) {
42109
+ err = filterError(err);
42110
+ next(err, job);
42111
+ });
42112
+ }
42113
+
42114
+ function done(err, job) {
42115
+ err = filterError(err);
42116
+ callback(err, job);
42117
+ }
42071
42118
  }
42072
42119
 
42073
42120
  function commandTakesFileInput(name) {
@@ -42114,23 +42161,19 @@ ${svg}
42114
42161
  });
42115
42162
  }
42116
42163
 
42164
+
42117
42165
  // Execute a sequence of parsed commands
42118
42166
  // @commands Array of parsed commands
42119
- // @job: Optional Job object containing previously imported data
42120
- // @cb: function(<error>, <catalog>)
42167
+ // @job: Job object containing previously imported data
42168
+ // @done: function([error], [job])
42121
42169
  //
42122
- function runParsedCommands(commands, job, cb) {
42123
- if (!job) {
42124
- job = new Job();
42125
- }
42126
-
42127
- if (!utils.isArray(commands)) {
42128
- error("Expected an array of parsed commands");
42129
- }
42130
-
42131
- if (commands.length === 0) {
42132
- return done(new UserError("No commands to run"));
42170
+ function runParsedCommands(commands, job, done) {
42171
+ if (!runningInBrowser() && commands[commands.length-1].name == 'o') {
42172
+ // in CLI, set 'final' flag on final -o command, so the export function knows
42173
+ // that it can modify the output dataset in-place instead of making a copy.
42174
+ commands[commands.length-1].options.final = true;
42133
42175
  }
42176
+ if (!job) job = new Job();
42134
42177
  commands = readAndRemoveSettings(job, commands);
42135
42178
  if (!runningInBrowser()) {
42136
42179
  printStartupMessages();
@@ -42139,31 +42182,13 @@ ${svg}
42139
42182
  if (commands.length === 0) {
42140
42183
  return done(null);
42141
42184
  }
42142
- if (!runningInBrowser() && commands[commands.length-1].name == 'o') {
42143
- // in CLI, set 'final' flag on final -o command, so the export function knows
42144
- // that it can modify the output dataset in-place instead of making a copy.
42145
- commands[commands.length-1].options.final = true;
42146
- }
42147
-
42148
- var groups = divideImportCommand(commands);
42149
- if (groups.length == 1) {
42150
- // run a simple sequence of commands (input files are not batched)
42151
- return runParsedCommands2(commands, job, done);
42152
- }
42153
-
42154
- // run duplicated commands (i.e. batch mode)
42155
- utils.reduceAsync(groups, job, nextGroup, done);
42156
-
42157
- function nextGroup(job, commands, next) {
42158
- runParsedCommands2(commands, job, function(err, job) {
42159
- err = filterError(err);
42160
- next(err, job);
42161
- });
42162
- }
42185
+ // we're no longer using the same Job for all batches -- no reset needed
42186
+ // // resetting closes any unterminated -if blocks from a previous command sequence
42187
+ // resetControlFlow(job);
42188
+ utils.reduceAsync(commands, job, nextCommand, done);
42163
42189
 
42164
- function done(err, job) {
42165
- err = filterError(err);
42166
- cb(err, job);
42190
+ function nextCommand(job, cmd, next) {
42191
+ runCommand(cmd, job, next);
42167
42192
  }
42168
42193
  }
42169
42194
 
@@ -42175,17 +42200,6 @@ ${svg}
42175
42200
  return err;
42176
42201
  }
42177
42202
 
42178
- function runParsedCommands2(commands, job, cb) {
42179
- // resetting closes any unterminated -if blocks from a previous command sequence
42180
- resetControlFlow(job);
42181
- utils.reduceAsync(commands, job, nextCommand, cb);
42182
-
42183
- function nextCommand(job, cmd, next) {
42184
- runCommand(cmd, job, next);
42185
- }
42186
- }
42187
-
42188
-
42189
42203
  // If an initial import command indicates that several input files should be
42190
42204
  // processed separately, then duplicate the sequence of commands to run
42191
42205
  // once for each input file
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "mapshaper",
3
- "version": "0.6.2",
3
+ "version": "0.6.5",
4
4
  "description": "A tool for editing vector datasets for mapping and GIS.",
5
5
  "keywords": [
6
6
  "shapefile",
@@ -36,7 +36,7 @@
36
36
  "/bin/**",
37
37
  "/www/**",
38
38
  "!/www/basemap.js",
39
- "!/www/nacis/",
39
+ "!/www/nacis/**",
40
40
  "/mapshaper.js",
41
41
  "!.DS_Store"
42
42
  ],
@@ -78,6 +78,7 @@
78
78
  get findValueByPct () { return findValueByPct; },
79
79
  get findValueByRank () { return findValueByRank; },
80
80
  get findMedian () { return findMedian; },
81
+ get findQuantile () { return findQuantile; },
81
82
  get mean () { return mean; },
82
83
  get format () { return format; },
83
84
  get formatter () { return formatter; },
@@ -2487,6 +2488,7 @@
2487
2488
  var historyId = 0;
2488
2489
  var _isOpen = false;
2489
2490
  var btn = gui.container.findChild('.console-btn').on('click', toggle);
2491
+ var globals = {}; // share user-defined globals between runs
2490
2492
 
2491
2493
  // expose this function, so other components can run commands (e.g. box tool)
2492
2494
  this.runMapshaperCommands = runMapshaperCommands;
@@ -2862,7 +2864,12 @@
2862
2864
  if (commands.length === 0) return done();
2863
2865
  applyParsedCommands(commands, function(err, flags) {
2864
2866
  if (!err) {
2865
- gui.session.consoleCommands(internal.standardizeConsoleCommands(str));
2867
+ str = internal.standardizeConsoleCommands(str);
2868
+ gui.session.consoleCommands(str);
2869
+ // kludge to terminate unclosed -if blocks
2870
+ if (str.includes('-if') && !str.includes('-endif')) {
2871
+ gui.session.consoleCommands('-endif');
2872
+ }
2866
2873
  }
2867
2874
  if (flags) {
2868
2875
  // if the command may have changed data, and a tool with an edit mode is being used,
@@ -2883,6 +2890,8 @@
2883
2890
  prevTableSize = prevTable ? prevTable.size() : 0,
2884
2891
  prevArcCount = prevArcs ? prevArcs.size() : 0,
2885
2892
  job = new internal.Job(model);
2893
+
2894
+ job.defs = globals; // share globals between runs
2886
2895
  internal.runParsedCommands(commands, job, function(err) {
2887
2896
  var flags = getCommandFlags(commands),
2888
2897
  active2 = model.getActiveLayer(),
@@ -5312,18 +5321,24 @@
5312
5321
  return arr[k];
5313
5322
  }
5314
5323
 
5315
- //
5316
- //
5317
5324
  function findMedian(arr) {
5318
- var n = arr.length,
5319
- rank = Math.floor(n / 2) + 1,
5320
- median = findValueByRank(arr, rank);
5321
- if ((n & 1) == 0) {
5322
- median = (median + findValueByRank(arr, rank - 1)) / 2;
5323
- }
5324
- return median;
5325
+ return findQuantile(arr, 0.5);
5325
5326
  }
5326
5327
 
5328
+ function findQuantile(arr, k) {
5329
+ var n = arr.length,
5330
+ i1 = Math.floor((n - 1) * k),
5331
+ i2 = Math.ceil((n - 1) * k);
5332
+ if (i1 < 0 || i2 >= n) return NaN;
5333
+ var v1 = findValueByRank(arr, i1 + 1);
5334
+ if (i1 == i2) return v1;
5335
+ var v2 = findValueByRank(arr, i2 + 1);
5336
+ // use linear interpolation
5337
+ var w1 = i2 / (n - 1) - k;
5338
+ var w2 = k - i1 / (n - 1);
5339
+ var v = (v1 * w1 + v2 * w2) * (n - 1);
5340
+ return v;
5341
+ }
5327
5342
 
5328
5343
  function mean(arr) {
5329
5344
  var count = 0,
@@ -8264,20 +8279,25 @@
8264
8279
  _frame;
8265
8280
 
8266
8281
  _position.on('resize', function(e) {
8267
- if (_contentBounds) {
8282
+ if (ready()) {
8268
8283
  onChange({resize: true});
8269
8284
  }
8270
8285
  });
8271
8286
 
8287
+ function ready() { return !!_contentBounds; }
8288
+
8272
8289
  this.reset = function() {
8290
+ if (!ready()) return;
8273
8291
  recenter(_contentBounds.centerX(), _contentBounds.centerY(), 1, {reset: true});
8274
8292
  };
8275
8293
 
8276
8294
  this.home = function() {
8295
+ if (!ready()) return;
8277
8296
  recenter(_contentBounds.centerX(), _contentBounds.centerY(), 1);
8278
8297
  };
8279
8298
 
8280
8299
  this.pan = function(xpix, ypix) {
8300
+ if (!ready()) return;
8281
8301
  var t = this.getTransform();
8282
8302
  recenter(_cx - xpix / t.mx, _cy - ypix / t.my);
8283
8303
  };
@@ -8285,6 +8305,7 @@
8285
8305
  // Zoom to @w (width of the map viewport in coordinates)
8286
8306
  // @xpct, @ypct: optional focus, [0-1]...
8287
8307
  this.zoomToExtent = function(w, xpct, ypct) {
8308
+ if (!ready()) return;
8288
8309
  if (arguments.length < 3) {
8289
8310
  xpct = 0.5;
8290
8311
  ypct = 0.5;
@@ -8304,6 +8325,7 @@
8304
8325
  };
8305
8326
 
8306
8327
  this.zoomByPct = function(pct, xpct, ypct) {
8328
+ if (!ready()) return;
8307
8329
  this.zoomToExtent(this.getBounds().width() / pct, xpct, ypct);
8308
8330
  };
8309
8331
 
package/www/mapshaper.js CHANGED
@@ -1,6 +1,6 @@
1
1
  (function () {
2
2
 
3
- var VERSION = "0.6.2";
3
+ var VERSION = "0.6.5";
4
4
 
5
5
 
6
6
  var utils = /*#__PURE__*/Object.freeze({
@@ -81,6 +81,7 @@
81
81
  get findValueByPct () { return findValueByPct; },
82
82
  get findValueByRank () { return findValueByRank; },
83
83
  get findMedian () { return findMedian; },
84
+ get findQuantile () { return findQuantile; },
84
85
  get mean () { return mean; },
85
86
  get format () { return format; },
86
87
  get formatter () { return formatter; },
@@ -832,18 +833,24 @@
832
833
  return arr[k];
833
834
  }
834
835
 
835
- //
836
- //
837
836
  function findMedian(arr) {
838
- var n = arr.length,
839
- rank = Math.floor(n / 2) + 1,
840
- median = findValueByRank(arr, rank);
841
- if ((n & 1) == 0) {
842
- median = (median + findValueByRank(arr, rank - 1)) / 2;
843
- }
844
- return median;
837
+ return findQuantile(arr, 0.5);
845
838
  }
846
839
 
840
+ function findQuantile(arr, k) {
841
+ var n = arr.length,
842
+ i1 = Math.floor((n - 1) * k),
843
+ i2 = Math.ceil((n - 1) * k);
844
+ if (i1 < 0 || i2 >= n) return NaN;
845
+ var v1 = findValueByRank(arr, i1 + 1);
846
+ if (i1 == i2) return v1;
847
+ var v2 = findValueByRank(arr, i2 + 1);
848
+ // use linear interpolation
849
+ var w1 = i2 / (n - 1) - k;
850
+ var w2 = k - i1 / (n - 1);
851
+ var v = (v1 * w1 + v2 * w2) * (n - 1);
852
+ return v;
853
+ }
847
854
 
848
855
  function mean(arr) {
849
856
  var count = 0,
@@ -10342,7 +10349,13 @@
10342
10349
  sum: captureNum,
10343
10350
  sums: capture,
10344
10351
  average: captureNum,
10352
+ mean: captureNum,
10345
10353
  median: captureNum,
10354
+ quantile: captureNum,
10355
+ iqr: captureNum,
10356
+ quartile1: captureNum,
10357
+ quartile2: captureNum,
10358
+ quartile3: captureNum,
10346
10359
  min: captureNum,
10347
10360
  max: captureNum,
10348
10361
  mode: capture,
@@ -10357,9 +10370,17 @@
10357
10370
  sum: wrap(utils.sum, 0),
10358
10371
  sums: wrap(sums),
10359
10372
  median: wrap(utils.findMedian),
10373
+ quantile: wrap2(utils.findQuantile),
10374
+ iqr: wrap(function(arr) {
10375
+ return utils.findQuantile(arr, 0.75) - utils.findQuantile(arr, 0.25);
10376
+ }),
10377
+ quartile1: wrap(function(arr) { return utils.findQuantile(arr, 0.25); }),
10378
+ quartile2: wrap(utils.findMedian),
10379
+ quartile3: wrap(function(arr) { return utils.findQuantile(arr, 0.75); }),
10360
10380
  min: wrap(min),
10361
10381
  max: wrap(max),
10362
10382
  average: wrap(utils.mean),
10383
+ mean: wrap(utils.mean),
10363
10384
  mode: wrap(getMode),
10364
10385
  collect: wrap(pass),
10365
10386
  first: wrap(pass),
@@ -10429,6 +10450,13 @@
10429
10450
  };
10430
10451
  }
10431
10452
 
10453
+ function wrap2(proc) {
10454
+ return function(arg1, arg2) {
10455
+ var c = colNo++;
10456
+ return rowNo > 0 ? proc(cols[c], arg2) : null;
10457
+ };
10458
+ }
10459
+
10432
10460
  function procAll() {
10433
10461
  for (var i=0; i<len; i++) {
10434
10462
  procRecord(i);
@@ -30912,7 +30940,7 @@ ${svg}
30912
30940
 
30913
30941
  var plasma = ramp(colors("0d088710078813078916078a19068c1b068d1d068e20068f2206902406912605912805922a05932c05942e05952f059631059733059735049837049938049a3a049a3c049b3e049c3f049c41049d43039e44039e46039f48039f4903a04b03a14c02a14e02a25002a25102a35302a35502a45601a45801a45901a55b01a55c01a65e01a66001a66100a76300a76400a76600a76700a86900a86a00a86c00a86e00a86f00a87100a87201a87401a87501a87701a87801a87a02a87b02a87d03a87e03a88004a88104a78305a78405a78606a68707a68808a68a09a58b0aa58d0ba58e0ca48f0da4910ea3920fa39410a29511a19613a19814a099159f9a169f9c179e9d189d9e199da01a9ca11b9ba21d9aa31e9aa51f99a62098a72197a82296aa2395ab2494ac2694ad2793ae2892b02991b12a90b22b8fb32c8eb42e8db52f8cb6308bb7318ab83289ba3388bb3488bc3587bd3786be3885bf3984c03a83c13b82c23c81c33d80c43e7fc5407ec6417dc7427cc8437bc9447aca457acb4679cc4778cc4977cd4a76ce4b75cf4c74d04d73d14e72d24f71d35171d45270d5536fd5546ed6556dd7566cd8576bd9586ada5a6ada5b69db5c68dc5d67dd5e66de5f65de6164df6263e06363e16462e26561e26660e3685fe4695ee56a5de56b5de66c5ce76e5be76f5ae87059e97158e97257ea7457eb7556eb7655ec7754ed7953ed7a52ee7b51ef7c51ef7e50f07f4ff0804ef1814df1834cf2844bf3854bf3874af48849f48948f58b47f58c46f68d45f68f44f79044f79143f79342f89441f89540f9973ff9983ef99a3efa9b3dfa9c3cfa9e3bfb9f3afba139fba238fca338fca537fca636fca835fca934fdab33fdac33fdae32fdaf31fdb130fdb22ffdb42ffdb52efeb72dfeb82cfeba2cfebb2bfebd2afebe2afec029fdc229fdc328fdc527fdc627fdc827fdca26fdcb26fccd25fcce25fcd025fcd225fbd324fbd524fbd724fad824fada24f9dc24f9dd25f8df25f8e125f7e225f7e425f6e626f6e826f5e926f5eb27f4ed27f3ee27f3f027f2f227f1f426f1f525f0f724f0f921"));
30914
30942
 
30915
- var lib = /*#__PURE__*/Object.freeze({
30943
+ var d3Scales = /*#__PURE__*/Object.freeze({
30916
30944
  __proto__: null,
30917
30945
  schemeCategory10: category10,
30918
30946
  schemeAccent: Accent,
@@ -31049,7 +31077,6 @@ ${svg}
31049
31077
  }
31050
31078
 
31051
31079
  function testLib() {
31052
- var lib = require('d3-scale-chromatic');
31053
31080
  schemes(index.categorical);
31054
31081
  schemes(index.sequential);
31055
31082
  schemes(index.diverging);
@@ -31059,7 +31086,7 @@ ${svg}
31059
31086
 
31060
31087
  function schemes(arr) {
31061
31088
  arr.forEach(function(name) {
31062
- if (!lib['scheme' + name]) {
31089
+ if (!d3Scales['scheme' + name]) {
31063
31090
  message('Warning: missing data for', name);
31064
31091
  }
31065
31092
  });
@@ -31067,7 +31094,7 @@ ${svg}
31067
31094
 
31068
31095
  function interpolators(arr) {
31069
31096
  arr.forEach(function(name) {
31070
- if (!lib['interpolate' + name]) {
31097
+ if (!d3Scales['interpolate' + name]) {
31071
31098
  message('Missing interpolator for', name);
31072
31099
  }
31073
31100
  });
@@ -31106,7 +31133,7 @@ ${svg}
31106
31133
  if (!isColorSchemeName(name)) {
31107
31134
  stop('Unknown color scheme name:', name);
31108
31135
  } else if (isCategoricalColorScheme(name)) {
31109
- colors = ramps[name] || require('d3-scale-chromatic')['scheme' + name];
31136
+ colors = ramps[name] || d3Scales['scheme' + name];
31110
31137
  } else {
31111
31138
  colors = getColorRamp(name, n);
31112
31139
  }
@@ -31140,9 +31167,8 @@ ${svg}
31140
31167
  function getColorRamp(name, n, stops) {
31141
31168
  initSchemes();
31142
31169
  name = standardName(name);
31143
- // var lib = require('d3-scale-chromatic');
31144
- var ramps = lib['scheme' + name];
31145
- var interpolate = lib['interpolate' + name];
31170
+ var ramps = d3Scales['scheme' + name];
31171
+ var interpolate = d3Scales['interpolate' + name];
31146
31172
  var ramp;
31147
31173
  if (!ramps && !interpolate) {
31148
31174
  stop('Unknown color scheme name:', name);
@@ -36778,6 +36804,7 @@ ${svg}
36778
36804
  } else {
36779
36805
  ctx = getNullLayerProxy(targets);
36780
36806
  }
36807
+ ctx.global = getStashedVar('defs') || {}; // TODO: remove duplication with mapshaper.expressions.mjs
36781
36808
  var exprOpts = Object.assign({returns: true}, opts);
36782
36809
  var func = compileExpressionToFunction(expr, exprOpts);
36783
36810
 
@@ -42056,6 +42083,13 @@ ${svg}
42056
42083
  inputObj = null;
42057
42084
  }
42058
42085
 
42086
+ if (commands.length === 0) {
42087
+ return callback(new UserError("No commands to run"));
42088
+ }
42089
+
42090
+ commands = runAndRemoveInfoCommands(commands);
42091
+ if (commands.length === 0) return done(null);
42092
+
42059
42093
  // add options to -i -o -join -clip -erase commands to bypass file i/o
42060
42094
  // TODO: find a less kludgy solution
42061
42095
  commands.forEach(function(cmd) {
@@ -42067,7 +42101,20 @@ ${svg}
42067
42101
  }
42068
42102
  });
42069
42103
 
42070
- runParsedCommands(commands, null, callback);
42104
+ var batches = divideImportCommand(commands);
42105
+ utils.reduceAsync(batches, null, nextGroup, done);
42106
+
42107
+ function nextGroup(prevJob, commands, next) {
42108
+ runParsedCommands(commands, new Job(), function(err, job) {
42109
+ err = filterError(err);
42110
+ next(err, job);
42111
+ });
42112
+ }
42113
+
42114
+ function done(err, job) {
42115
+ err = filterError(err);
42116
+ callback(err, job);
42117
+ }
42071
42118
  }
42072
42119
 
42073
42120
  function commandTakesFileInput(name) {
@@ -42114,23 +42161,19 @@ ${svg}
42114
42161
  });
42115
42162
  }
42116
42163
 
42164
+
42117
42165
  // Execute a sequence of parsed commands
42118
42166
  // @commands Array of parsed commands
42119
- // @job: Optional Job object containing previously imported data
42120
- // @cb: function(<error>, <catalog>)
42167
+ // @job: Job object containing previously imported data
42168
+ // @done: function([error], [job])
42121
42169
  //
42122
- function runParsedCommands(commands, job, cb) {
42123
- if (!job) {
42124
- job = new Job();
42125
- }
42126
-
42127
- if (!utils.isArray(commands)) {
42128
- error("Expected an array of parsed commands");
42129
- }
42130
-
42131
- if (commands.length === 0) {
42132
- return done(new UserError("No commands to run"));
42170
+ function runParsedCommands(commands, job, done) {
42171
+ if (!runningInBrowser() && commands[commands.length-1].name == 'o') {
42172
+ // in CLI, set 'final' flag on final -o command, so the export function knows
42173
+ // that it can modify the output dataset in-place instead of making a copy.
42174
+ commands[commands.length-1].options.final = true;
42133
42175
  }
42176
+ if (!job) job = new Job();
42134
42177
  commands = readAndRemoveSettings(job, commands);
42135
42178
  if (!runningInBrowser()) {
42136
42179
  printStartupMessages();
@@ -42139,31 +42182,13 @@ ${svg}
42139
42182
  if (commands.length === 0) {
42140
42183
  return done(null);
42141
42184
  }
42142
- if (!runningInBrowser() && commands[commands.length-1].name == 'o') {
42143
- // in CLI, set 'final' flag on final -o command, so the export function knows
42144
- // that it can modify the output dataset in-place instead of making a copy.
42145
- commands[commands.length-1].options.final = true;
42146
- }
42147
-
42148
- var groups = divideImportCommand(commands);
42149
- if (groups.length == 1) {
42150
- // run a simple sequence of commands (input files are not batched)
42151
- return runParsedCommands2(commands, job, done);
42152
- }
42153
-
42154
- // run duplicated commands (i.e. batch mode)
42155
- utils.reduceAsync(groups, job, nextGroup, done);
42156
-
42157
- function nextGroup(job, commands, next) {
42158
- runParsedCommands2(commands, job, function(err, job) {
42159
- err = filterError(err);
42160
- next(err, job);
42161
- });
42162
- }
42185
+ // we're no longer using the same Job for all batches -- no reset needed
42186
+ // // resetting closes any unterminated -if blocks from a previous command sequence
42187
+ // resetControlFlow(job);
42188
+ utils.reduceAsync(commands, job, nextCommand, done);
42163
42189
 
42164
- function done(err, job) {
42165
- err = filterError(err);
42166
- cb(err, job);
42190
+ function nextCommand(job, cmd, next) {
42191
+ runCommand(cmd, job, next);
42167
42192
  }
42168
42193
  }
42169
42194
 
@@ -42175,17 +42200,6 @@ ${svg}
42175
42200
  return err;
42176
42201
  }
42177
42202
 
42178
- function runParsedCommands2(commands, job, cb) {
42179
- // resetting closes any unterminated -if blocks from a previous command sequence
42180
- resetControlFlow(job);
42181
- utils.reduceAsync(commands, job, nextCommand, cb);
42182
-
42183
- function nextCommand(job, cmd, next) {
42184
- runCommand(cmd, job, next);
42185
- }
42186
- }
42187
-
42188
-
42189
42203
  // If an initial import command indicates that several input files should be
42190
42204
  // processed separately, then duplicate the sequence of commands to run
42191
42205
  // once for each input file