├── .gitignore
├── .jshintrc
├── .npmignore
├── README.md
├── bower.json
├── dist
├── shp.js
└── shp.min.js
├── files
├── Readme.txt
├── TM_WORLD_BORDERS_SIMPL-0.3.dbf
├── TM_WORLD_BORDERS_SIMPL-0.3.shp
├── TM_WORLD_BORDERS_SIMPL-0.3.shx
├── TM_WORLD_BORDERS_SIMPL-0.3.zip
├── counties5.zip
├── empty-shp.zip
├── maSP.zip
├── nj_counties.zip
├── nj_muni.zip
├── pandr.dbf
├── pandr.prj
├── pandr.qpj
├── pandr.sbn
├── pandr.sbx
├── pandr.shp
├── pandr.shp.xml
├── pandr.shx
└── pandr.zip
├── index.html
├── lib
├── binaryajax-browser.js
├── binaryajax.js
├── index.js
├── parseShp.js
└── unzip.js
├── package.json
├── site
├── catiline.js
├── curl.js
├── gh-fork-ribbon.css
├── images
│ ├── layers-2x.png
│ ├── layers.png
│ ├── marker-icon-2x.png
│ ├── marker-icon.png
│ └── marker-shadow.png
├── leaflet.css
├── leaflet.ie.css
├── leaflet.js
├── leaflet.zip
├── map.html
├── proj-small.html
├── proj.html
└── require.js
└── test
├── bundle.js
├── data
├── bad.dbf
├── bad.shp
├── badzip.zip
├── codepage.cpg
├── codepage.dbf
├── codepage.prj
├── codepage.qpj
├── codepage.shp
├── codepage.shx
├── codepage.zip
├── counties.dbf
├── counties.sbn
├── counties.sbx
├── counties.shp
├── counties.shp.xml
├── counties.shx
├── counties.zip
├── mixedcase.zip
├── noshp.zip
├── senate.dbf
├── senate.prj
├── senate.sbn
├── senate.sbx
├── senate.shp
├── senate.shp.xml
├── senate.shx
├── senate.zip
├── train_stations.zip
├── utf.cpg
├── utf.dbf
├── utf.prj
├── utf.qpj
├── utf.shp
├── utf.shx
└── utf.zip
├── index.html
└── test.js
/.gitignore:
--------------------------------------------------------------------------------
1 | *~
2 | node_modules
3 | .c9revisions
4 | jam
5 | components
6 | .DS_Store
--------------------------------------------------------------------------------
/.jshintrc:
--------------------------------------------------------------------------------
1 | {
2 | "node" : true,
3 | "browser" : true,
4 | "curly": true,
5 | "latedef": "nofunc",
6 | "eqeqeq": true,
7 | "immed": true,
8 | "newcap": true,
9 | "noarg": true,
10 | "sub": true,
11 | "undef": "nofunc",
12 | "strict": true,
13 | "white": true,
14 | "indent": 2,
15 | "trailing": true,
16 | "quotmark": "single"
17 | }
--------------------------------------------------------------------------------
/.npmignore:
--------------------------------------------------------------------------------
1 | test
2 | site
3 | files
4 | jam
5 | *.zip
6 | *.geojson
7 | *.topojson
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Shapefile.js
2 |
3 | If you are having encoding issues in internet explorer please include [this script](https://cdn.rawgit.com/calvinmetcalf/text-encoding/4aff951959085f74a5872aeed8d79ec95b6c74c3/lib/encoding-indexes.js) as well.
4 |
5 | Redoing all of this in modern JS. Promises, Typed Arrays, other hipster things, I wouldn't say it's based on [RandomEtc's version](https://github.com/RandomEtc/shapefile-js) as much as inspired by it as there is 0 code shared and I really only read the binary ajax part of his (hence why my function has the same name, they are otherwise not related). My sources were:
6 |
7 | - [wikipedia article](https://en.wikipedia.org/wiki/Shapefile)
8 | - [ESRI white paper](http://www.esri.com/library/whitepapers/pdfs/shapefile.pdf)
9 | - [This page on Xbase](http://www.clicketyclick.dk/databases/xbase/format/dbf.html)
10 |
11 | ## Demos
12 |
13 | - [Countries/zipfile](http://calvinmetcalf.github.io/shapefile-js)
14 | - [Google maps](http://calvinmetcalf.github.io/shapefile-js/site/map.html)
15 | - [Local Zipfile](http://leaflet.calvinmetcalf.com)
16 | - [Projected big with web workers](http://calvinmetcalf.github.io/shapefile-js/site/proj.html)
17 | - [Projected small](http://calvinmetcalf.github.io/shapefile-js/site/proj-small.html)
18 |
19 | ## Usage
20 |
21 | For use with [browserify](http://browserify.org/), [webpack](https://webpack.github.io/):
22 |
23 | npm install shpjs --save
24 |
25 | Or include directly in your webpage from:
26 |
27 | https://unpkg.com/shpjs@latest/dist/shp.js
28 |
29 | ## API
30 |
31 | Has a function `shp` which accepts a string which is the path the she shapefile minus the extension and returns a promise which resolves into geojson.
32 |
33 | ```javascript
34 | //for the shapefiles in the folder called 'files' with the name pandr.shp
35 | shp("files/pandr").then(function(geojson){
36 | //do something with your geojson
37 | });
38 | ```
39 | or you can call it on a .zip file which contains the shapefile
40 |
41 | ```javascript
42 | //for the shapefiles in the files folder called pandr.shp
43 | shp("files/pandr.zip").then(function(geojson){
44 | //see bellow for whats here this internally call shp.parseZip()
45 | });
46 | ```
47 |
48 | or if you got the zip some other way (like the [File API](https://developer.mozilla.org/en-US/docs/Web/API/File)) then with the arrayBuffer you can call
49 |
50 | ```javascript
51 | shp(buffer).then(function(geojson){});
52 | //or
53 | shp.parseZip(buffer)->returns zip
54 | ```
55 | If there is only one shp in the zipefile it returns geojson, if there are multiple then it will be an array. All of the geojson objects have an extra key `fileName` the value of which is the
56 | name of the shapefile minus the extension (I.E. the part of the name that's the same for all of them)
57 |
58 | You could also load the arraybuffers seperately:
59 |
60 | ```javascript
61 | shp.combine([shp.parseShp(shpBuffer, /*optional prj str*/),shp.parseDbf(dbfBuffer)]);
62 | ```
63 |
64 | ## Stick it in a worker
65 |
66 | I used my library [catiline](http://catilinejs.com/) to parallelize the demos to do so I changed
67 |
68 | ```html
69 |
70 |
75 | ```
76 |
77 | to
78 |
79 | ```html
80 |
81 |
91 | ```
92 |
93 | to send the worker a buffer from the file api you'd do (I'm omitting where you include the catiline script)
94 |
95 | ```javascript
96 | var worker = cw(function(data){
97 | importScripts('../dist/shp.js');
98 | return shp.parseZip(data);
99 | });
100 |
101 | worker.data(reader.result,[reader.result]).then(function(data){
102 | //do stuff with data
103 | });
104 | ```
105 |
106 | ## Done
107 |
108 | - Binary Ajax
109 | - parsing the shp
110 | - parse the dbf
111 | - join em
112 | - zip
113 | - file api
114 | - Some Projections
115 | - More Projections
116 |
117 | ## to do
118 |
119 | - check for geometry validity.
120 | - Tests
121 |
122 |
123 | ## LICENSE
124 | Main library MIT license, original version was less permissive but there is 0 code shared. Included libraries are under their respective lisenses which are:
125 | - [JSZip](https://github.com/Stuk/jszip/) by @Stuk MIT or GPLv3
126 | - [lie](https://github.com/calvinmetcalf/lie) by me and @RubenVerborgh MIT
127 | - [setImmediate](https://github.com/NobleJS/setImmediate) by @NobleJS et al MIT
128 | - [World Borders shapefile](http://thematicmapping.org/downloads/world_borders.php) is CC-BY-SA 3.0.
129 | - Park and Ride shapefile is from [MassDOT](http://mass.gov/massdot) and is public domain.
130 | - MA town boundaries from [MassGIS](http://www.mass.gov/anf/research-and-tech/it-serv-and-support/application-serv/office-of-geographic-information-massgis/) and is public domain
131 | - NJ County Boundaries from [NJgin](https://njgin.state.nj.us/NJ_NJGINExplorer/index.jsp) and should be public domain.
132 | - [Proj4js](https://github.com/proj4js/proj4js) by me et al MIT
133 |
134 | [](https://david-dm.org/calvinmetcalf/shapefile-js)
135 | [](https://david-dm.org/calvinmetcalf/shapefile-js#info=devDependencies)
136 | [](https://david-dm.org/calvinmetcalf/shapefile-js#info=peerDependencies)
137 |
--------------------------------------------------------------------------------
/bower.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "shp",
3 | "version": "3.3.2",
4 | "description": "A binary shapefile loader, for javascript. Not many caveats",
5 | "homepage": "https://github.com/calvinmetcalf/shapefile-js",
6 | "authors": [
7 | "Calvin Metcalf "
8 | ],
9 | "main": "dist/shp.js",
10 | "keywords": [
11 | "shp",
12 | "gis",
13 | "geojson"
14 | ],
15 | "license": "MIT",
16 | "ignore": [
17 | "**/.*",
18 | "node_modules",
19 | "bower_components",
20 | "test",
21 | "tests"
22 | ]
23 | }
24 |
--------------------------------------------------------------------------------
/files/Readme.txt:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/Readme.txt
--------------------------------------------------------------------------------
/files/TM_WORLD_BORDERS_SIMPL-0.3.dbf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/TM_WORLD_BORDERS_SIMPL-0.3.dbf
--------------------------------------------------------------------------------
/files/TM_WORLD_BORDERS_SIMPL-0.3.shp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/TM_WORLD_BORDERS_SIMPL-0.3.shp
--------------------------------------------------------------------------------
/files/TM_WORLD_BORDERS_SIMPL-0.3.shx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/TM_WORLD_BORDERS_SIMPL-0.3.shx
--------------------------------------------------------------------------------
/files/TM_WORLD_BORDERS_SIMPL-0.3.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/TM_WORLD_BORDERS_SIMPL-0.3.zip
--------------------------------------------------------------------------------
/files/counties5.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/counties5.zip
--------------------------------------------------------------------------------
/files/empty-shp.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/empty-shp.zip
--------------------------------------------------------------------------------
/files/maSP.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/maSP.zip
--------------------------------------------------------------------------------
/files/nj_counties.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/nj_counties.zip
--------------------------------------------------------------------------------
/files/nj_muni.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/nj_muni.zip
--------------------------------------------------------------------------------
/files/pandr.dbf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/pandr.dbf
--------------------------------------------------------------------------------
/files/pandr.prj:
--------------------------------------------------------------------------------
1 | GEOGCS["GCS_WGS_1984",DATUM["D_WGS_1984",SPHEROID["WGS_1984",6378137.0,298.257223563]],PRIMEM["Greenwich",0.0],UNIT["Degree",0.0174532925199433]]
--------------------------------------------------------------------------------
/files/pandr.qpj:
--------------------------------------------------------------------------------
1 | GEOGCS["WGS 84",DATUM["WGS_1984",SPHEROID["WGS 84",6378137,298.257223563,AUTHORITY["EPSG","7030"]],AUTHORITY["EPSG","6326"]],PRIMEM["Greenwich",0,AUTHORITY["EPSG","8901"]],UNIT["degree",0.01745329251994328,AUTHORITY["EPSG","9122"]],AUTHORITY["EPSG","4326"]]
2 |
--------------------------------------------------------------------------------
/files/pandr.sbn:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/pandr.sbn
--------------------------------------------------------------------------------
/files/pandr.sbx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/pandr.sbx
--------------------------------------------------------------------------------
/files/pandr.shp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/pandr.shp
--------------------------------------------------------------------------------
/files/pandr.shp.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | 20120530 08362400 FALSE CreateFeatureclass "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.PublicFacilities" ParkAndRide # Export_Output_2_Layer SAME_AS_TEMPLATE SAME_AS_TEMPLATE "PROJCS['NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001',GEOGCS['GCS_North_American_1983',DATUM['D_North_American_1983',SPHEROID['GRS_1980',6378137.0,298.257222101]],PRIMEM['Greenwich',0.0],UNIT['Degree',0.0174532925199433]],PROJECTION['Lambert_Conformal_Conic'],PARAMETER['False_Easting',200000.0],PARAMETER['False_Northing',750000.0],PARAMETER['Central_Meridian',-71.5],PARAMETER['Standard_Parallel_1',41.71666666666667],PARAMETER['Standard_Parallel_2',42.68333333333333],PARAMETER['Latitude_Of_Origin',41.0],UNIT['Meter',1.0]];-361489.141077092 327975.618391579 1953.12499818101;0 1;0 1" # 0 0 0 "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.PublicFacilities\gisvector.GISADMIN.ParkAndRide" Append Export_Output_2_Layer "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.PublicFacilities\gisvector.GISADMIN.ParkAndRide" TEST "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.PublicFacilities\gisvector.GISADMIN.ParkAndRide" FeatureClassToFeatureClass S:\HQ\Planning\DataResources\Workspace\PaulN\ParknRide\ParkandRide-PN.mdb\Export_Output_2 "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.PublicFacilities" ParkAndRide # "TOWN TOWN VISIBLE;LOCATION LOCATION VISIBLE;STATUS STATUS VISIBLE;DISTRICT DISTRICT VISIBLE;OPERATOR OPERATOR VISIBLE;BIKE_RACKS BIKE_RACKS VISIBLE;SHELTERS SHELTERS VISIBLE;PHONES PHONES VISIBLE;LIGHTS LIGHTS VISIBLE;FENCES FENCES VISIBLE;SIGNS SIGNS VISIBLE;OWNER OWNER VISIBLE;CAPACITY CAPACITY VISIBLE;BUS_SERVICE BUS_SERVICE VISIBLE;RAIL_SERVICE RAIL_SERVICE VISIBLE;BOAT_SERVICE BOAT_SERVICE VISIBLE;MAP_ID MAP_ID VISIBLE;MPO MPO VISIBLE" SAME_AS_TEMPLATE SAME_AS_TEMPLATE # 0 "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.PublicFacilities\gisvector.GISADMIN.ParkAndRide" FeatureClassToFeatureClass "Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots" S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb Update2009 # "TOWN 'TOWN' true true false 25 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,TOWN,-1,-1;LOCATION 'LOCATION' true true false 45 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,LOCATION,-1,-1;STATUS 'STATUS' true true false 15 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,STATUS,-1,-1;DISTRICT 'DISTRICT' true true false 4 Long 0 10 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,DISTRICT,-1,-1;OPERATOR 'OPERATOR' true true false 25 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,OPERATOR,-1,-1;BIKE_RACKS 'BIKE_RACKS' true true false 3 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,BIKE_RACKS,-1,-1;SHELTERS 'SHELTERS' true true false 3 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,SHELTERS,-1,-1;PHONES 'PHONES' true true false 3 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,PHONES,-1,-1;LIGHTS 'LIGHTS' true true false 3 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,LIGHTS,-1,-1;FENCES 'FENCES' true true false 3 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,FENCES,-1,-1;SIGNS 'SIGNS' true true false 3 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,SIGNS,-1,-1;OWNER 'OWNER' true true false 15 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,OWNER,-1,-1;CAPACITY 'CAPACITY' true true false 4 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,CAPACITY,-1,-1;BUS_SERVICE 'BUS_SERVICE' true true false 25 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,BUS_SERVICE,-1,-1;RAIL_SERVICE 'RAIL_SERVICE' true true false 10 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,RAIL_SERVICE,-1,-1;BOAT_SERVICE 'BOAT_SERVICE' true true false 10 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,BOAT_SERVICE,-1,-1;MAP_ID 'MAP_ID' true true false 4 Long 0 10 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,MAP_ID,-1,-1;MPO 'MPO' true true false 50 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,MPO,-1,-1;SYMBOL 'SYMBOL' true true false 1 Text 0 0 ,First,#,Database Connections\MassDOT GIS.sde\gisVector.GISADMIN.Transportation\gisvector.GISADMIN.ParkAndRideLots,SYMBOL,-1,-1" # S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009 FeatureClassToFeatureClass S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009 "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Transportation" ParkAndRide # "TOWN 'TOWN' true true false 25 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,TOWN,-1,-1;LOCATION 'LOCATION' true true false 45 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,LOCATION,-1,-1;STATUS 'STATUS' true true false 15 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,STATUS,-1,-1;DISTRICT 'DISTRICT' true true false 4 Long 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,DISTRICT,-1,-1;OPERATOR 'OPERATOR' true true false 25 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,OPERATOR,-1,-1;BIKE_RACKS 'BIKE_RACKS' true true false 3 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,BIKE_RACKS,-1,-1;SHELTERS 'SHELTERS' true true false 3 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,SHELTERS,-1,-1;PHONES 'PHONES' true true false 3 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,PHONES,-1,-1;LIGHTS 'LIGHTS' true true false 3 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,LIGHTS,-1,-1;FENCES 'FENCES' true true false 3 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,FENCES,-1,-1;SIGNS 'SIGNS' true true false 3 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,SIGNS,-1,-1;OWNER 'OWNER' true true false 15 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,OWNER,-1,-1;CAPACITY 'CAPACITY' true true false 4 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,CAPACITY,-1,-1;BUS_SERVICE 'BUS_SERVICE' true true false 25 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,BUS_SERVICE,-1,-1;RAIL_SERVICE 'RAIL_SERVICE' true true false 10 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,RAIL_SERVICE,-1,-1;BOAT_SERVICE 'BOAT_SERVICE' true true false 10 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,BOAT_SERVICE,-1,-1;MAP_ID 'MAP_ID' true true false 4 Long 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,MAP_ID,-1,-1;MPO 'MPO' true true false 50 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,MPO,-1,-1;SYMBOL 'SYMBOL' true true false 1 Text 0 0 ,First,#,S:\HQ\Planning\DataResources\Workspace\Paul\ParkAndRideUpdate.mdb\Update2009,SYMBOL,-1,-1" # "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Transportation\GISVECTOR.GISADMIN.ParkAndRide" Project "Database Connections\wh.sde\gisvector.GISADMIN.Facilities\gisVector.GISADMIN.ParkandRideLot" "C:\Documents and Settings\MetcalfC\Desktop\pandr.shp" GEOGCS['GCS_WGS_1984',DATUM['D_WGS_1984',SPHEROID['WGS_1984',6378137.0,298.257223563]],PRIMEM['Greenwich',0.0],UNIT['Degree',0.0174532925199433]] NAD_1983_To_WGS_1984_1 PROJCS['NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001',GEOGCS['GCS_North_American_1983',DATUM['D_North_American_1983',SPHEROID['GRS_1980',6378137.0,298.257222101]],PRIMEM['Greenwich',0.0],UNIT['Degree',0.0174532925199433]],PROJECTION['Lambert_Conformal_Conic'],PARAMETER['False_Easting',200000.0],PARAMETER['False_Northing',750000.0],PARAMETER['Central_Meridian',-71.5],PARAMETER['Standard_Parallel_1',41.71666666666667],PARAMETER['Standard_Parallel_2',42.68333333333333],PARAMETER['Latitude_Of_Origin',41.0],UNIT['Meter',1.0]] 20091218 06265300 20091218 06265300 1.0 Microsoft Windows XP Version 5.1 (Build 2600) Service Pack 3; ESRI ArcCatalog 9.3.1.3000 en REQUIRED: A brief narrative summary of the data set. REQUIRED: A summary of the intentions with which the data set was developed. REQUIRED: The name of an organization or individual that developed the data set. REQUIRED: The date when the data set is published or otherwise made available for release. GISVECTOR.GISADMIN.ParkAndRide GISVECTOR.GISADMIN.ParkAndRide vector digital data Server=mhd-gis-wh; Service=sde:sqlserver:mhd-gis-wh; Database=gisVector; User=gisadmin; Version=sde.DEFAULT REQUIRED: The basis on which the time period of content information is determined. REQUIRED: The year (and optionally month, or month and day) for which the data set corresponds to the ground. REQUIRED: The state of the data set. REQUIRED: The frequency with which changes and additions are made to the data set after the initial data set is completed. REQUIRED: Western-most coordinate of the limit of coverage expressed in longitude. REQUIRED: Eastern-most coordinate of the limit of coverage expressed in longitude. REQUIRED: Northern-most coordinate of the limit of coverage expressed in latitude. REQUIRED: Southern-most coordinate of the limit of coverage expressed in latitude. REQUIRED: Reference to a formally registered thesaurus or a similar authoritative source of theme keywords. REQUIRED: Common-use word or phrase used to describe the subject of the data set. REQUIRED: Restrictions and legal prerequisites for accessing the data set. REQUIRED: Restrictions and legal prerequisites for using the data set after access is granted. SDE Feature Class Microsoft Windows XP Version 5.1 (Build 2600) Service Pack 3; ESRI ArcCatalog 9.3.1.3000 GISVECTOR.GISADMIN.ParkAndRide en FGDC Content Standards for Digital Geospatial Metadata FGDC-STD-001-1998 local time REQUIRED: The person responsible for the metadata information. REQUIRED: The organization responsible for the metadata information. REQUIRED: The mailing and/or physical address for the organization or individual. REQUIRED: The city of the address. REQUIRED: The state or province of the address. REQUIRED: The ZIP or other postal code of the address. REQUIRED: The telephone number by which individuals can speak to the organization or individual. 20091218 http://www.esri.com/metadata/esriprof80.html ESRI Metadata Profile ISO 19115 Geographic Information - Metadata DIS_ESRI1.0 dataset Downloadable Data 002 Server=mhd-gis-wh; Service=sde:sqlserver:mhd-gis-wh; Database=gisVector; User=gisadmin; Version=sde.DEFAULT ArcSDE Connection SDE Feature Class Vector Simple Point FALSE 0 TRUE FALSE Entity point 0 GCS_North_American_1983 NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001 coordinate pair meters 0.000512 0.000512 State Plane Coordinate System 1983 2001 41.716667 42.683333 -71.500000 41.000000 200000.000000 750000.000000 North American Datum of 1983 Geodetic Reference System 80 6378137.000000 298.257222 Explicit elevation coordinate included with horizontal coordinates 1.000000 NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001 0 GISVECTOR.GISADMIN.ParkAndRide Feature Class 0 OBJECTID OBJECTID OID 4 10 0 Internal feature number. ESRI Sequential unique whole numbers that are automatically generated. Shape Shape Geometry 4 0 0 Feature geometry. ESRI Coordinates defining the features. TOWN TOWN String 25 0 0 LOCATION LOCATION String 45 0 0 STATUS STATUS String 15 0 0 DISTRICT DISTRICT Integer 4 10 0 OPERATOR OPERATOR String 25 0 0 BIKE_RACKS BIKE_RACKS String 3 0 0 SHELTERS SHELTERS String 3 0 0 PHONES PHONES String 3 0 0 LIGHTS LIGHTS String 3 0 0 FENCES FENCES String 3 0 0 SIGNS SIGNS String 3 0 0 OWNER OWNER String 15 0 0 CAPACITY CAPACITY String 4 0 0 BUS_SERVICE BUS_SERVICE String 25 0 0 RAIL_SERVICE RAIL_SERVICE String 10 0 0 BOAT_SERVICE BOAT_SERVICE String 10 0 0 MAP_ID MAP_ID Integer 4 10 0 MPO MPO String 50 0 0 SYMBOL SYMBOL String 1 0 0 20091218 Dataset copied. Server=mhd-gis-wh; Service=esri_sde; Database=gisvector; User=gisviewer; Version=sde.DEFAULT 20100813 07273100
4 |
--------------------------------------------------------------------------------
/files/pandr.shx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/pandr.shx
--------------------------------------------------------------------------------
/files/pandr.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/files/pandr.zip
--------------------------------------------------------------------------------
/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Shapefile in Leaflet!
9 |
10 |
13 |
14 |
15 |
24 |
29 |
30 |
47 |
48 |
--------------------------------------------------------------------------------
/lib/binaryajax-browser.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 | var Promise = require('lie');
3 | module.exports = binaryAjax;
4 | function binaryAjax(url){
5 | return new Promise(function(resolve,reject){
6 | var type = url.slice(-3);
7 | var ajax = new XMLHttpRequest();
8 | ajax.open('GET',url,true);
9 | if(type !== 'prj' && type !== 'cpg'){
10 | ajax.responseType='arraybuffer';
11 | }
12 | ajax.addEventListener('load', function (){
13 | if(ajax.status>399){
14 | if(type==='prj' || type === 'cpg'){
15 | return resolve(false);
16 | }else{
17 | return reject(new Error(ajax.status));
18 | }
19 | }
20 | if(type !== 'prj' && type !== 'cpg'){
21 | return resolve(new Buffer(ajax.response));
22 | } else {
23 | return resolve(ajax.response);
24 | }
25 | }, false);
26 | ajax.send();
27 | });
28 | }
29 |
--------------------------------------------------------------------------------
/lib/binaryajax.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 | var Promise = require('lie');
3 | var http = require('http');
4 | var https = require('https');
5 | var Url = require('url');
6 |
7 | module.exports = binaryAjax;
8 |
9 | function binaryAjax(url) {
10 | return new Promise(function(resolve, reject) {
11 | var type = url.slice(-3);
12 | var parsed = Url.parse(url);
13 | var method = http;
14 | if (parsed.protocol === 'https:') {
15 | method = https;
16 | }
17 | method.get(parsed, function(res) {
18 | var len = 0;
19 | var buffers = [];
20 |
21 | res.on('data', function(d) {
22 | len += d.length;
23 | buffers.push(d);
24 | });
25 | res.on('error', function(e) {
26 | reject(e);
27 | });
28 | res.on('end', function() {
29 | if (res.statusCode > 399) {
30 | if (type === 'prj' || type === 'cpg') {
31 | return resolve(false);
32 | } else {
33 | return reject(new Error(Buffer.concat(buffers, len).toString()));
34 | }
35 | }
36 | var buffer = Buffer.concat(buffers, len);
37 | if (type === 'prj') {
38 | resolve(buffer.toString());
39 | } else {
40 | resolve(buffer);
41 | }
42 | });
43 | }).on('error', function(e) {
44 | reject(e);
45 | });
46 | });
47 | }
48 |
--------------------------------------------------------------------------------
/lib/index.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 | var proj4 = require('proj4');
3 | var unzip = require('./unzip');
4 | var binaryAjax = require('./binaryajax');
5 | var parseShp = require('./parseShp');
6 | var parseDbf = require('parsedbf');
7 | var Promise = require('lie');
8 | var Cache = require('lru-cache');
9 | var cache = new Cache({
10 | max: 20
11 | });
12 |
13 | function toBuffer(b) {
14 | if (!b) {
15 | throw new Error('forgot to pass buffer');
16 | }
17 | if (Buffer.isBuffer(b)) {
18 | return b;
19 | }
20 | if (b instanceof global.ArrayBuffer) {
21 | return new Buffer(b);
22 | }
23 | if (b.buffer instanceof global.ArrayBuffer) {
24 | if (b.BYTES_PER_ELEMENT === 1) {
25 | return new Buffer(b);
26 | }
27 | return new Buffer(b.buffer);
28 | }
29 | }
30 |
31 | function shp(base, whiteList) {
32 | if (typeof base === 'string' && cache.has(base)) {
33 | return Promise.resolve(cache.get(base));
34 | }
35 | return shp.getShapefile(base, whiteList).then(function(resp) {
36 | if (typeof base === 'string') {
37 | cache.set(base, resp);
38 | }
39 | return resp;
40 | });
41 | }
42 | shp.combine = function(arr) {
43 | var out = {};
44 | out.type = 'FeatureCollection';
45 | out.features = [];
46 | var i = 0;
47 | var len = arr[0].length;
48 | while (i < len) {
49 | out.features.push({
50 | 'type': 'Feature',
51 | 'geometry': arr[0][i],
52 | 'properties': arr[1][i]
53 | });
54 | i++;
55 | }
56 | return out;
57 | };
58 | shp.parseZip = function(buffer, whiteList) {
59 | var key;
60 | buffer = toBuffer(buffer);
61 | var zip = unzip(buffer);
62 | var names = [];
63 | whiteList = whiteList || [];
64 | for (key in zip) {
65 | if (key.indexOf('__MACOSX') !== -1) {
66 | continue;
67 | }
68 | if (key.slice(-3).toLowerCase() === 'shp') {
69 | names.push(key.slice(0, -4));
70 | zip[key.slice(0, -3) + key.slice(-3).toLowerCase()] = zip[key];
71 | } else if (key.slice(-3).toLowerCase() === 'prj') {
72 | zip[key.slice(0, -3) + key.slice(-3).toLowerCase()] = proj4(zip[key]);
73 | } else if (key.slice(-4).toLowerCase() === 'json' || whiteList.indexOf(key.split('.').pop()) > -1) {
74 | names.push(key.slice(0, -3) + key.slice(-3).toLowerCase());
75 | } else if (key.slice(-3).toLowerCase() === 'dbf' || key.slice(-3).toLowerCase() === 'cpg') {
76 | zip[key.slice(0, -3) + key.slice(-3).toLowerCase()] = zip[key];
77 | }
78 | }
79 | if (!names.length) {
80 | throw new Error('no layers founds');
81 | }
82 | var geojson = names.map(function(name) {
83 | var parsed, dbf;
84 | var lastDotIdx = name.lastIndexOf('.');
85 | if (lastDotIdx > -1 && name.slice(lastDotIdx).indexOf('json') > -1) {
86 | parsed = JSON.parse(zip[name]);
87 | parsed.fileName = name.slice(0, lastDotIdx);
88 | } else if (whiteList.indexOf(name.slice(lastDotIdx + 1)) > -1) {
89 | parsed = zip[name];
90 | parsed.fileName = name;
91 | } else {
92 | if (zip[name + '.dbf']) {
93 | dbf = parseDbf(zip[name + '.dbf'], zip[name + '.cpg']);
94 | }
95 | parsed = shp.combine([parseShp(zip[name + '.shp'], zip[name + '.prj']), dbf]);
96 | parsed.fileName = name;
97 | }
98 | return parsed;
99 | });
100 | if (geojson.length === 1) {
101 | return geojson[0];
102 | } else {
103 | return geojson;
104 | }
105 | };
106 |
107 | function getZip(base, whiteList) {
108 | return binaryAjax(base).then(function(a) {
109 | return shp.parseZip(a, whiteList);
110 | });
111 | }
112 | shp.getShapefile = function(base, whiteList) {
113 | if (typeof base === 'string') {
114 | if (base.slice(-4).toLowerCase() === '.zip') {
115 | return getZip(base, whiteList);
116 | } else {
117 | return Promise.all([
118 | Promise.all([
119 | binaryAjax(base + '.shp'),
120 | binaryAjax(base + '.prj')
121 | ]).then(function(args) {
122 | return parseShp(args[0], args[1] ? proj4(args[1]) : false);
123 | }),
124 | Promise.all([
125 | binaryAjax(base + '.dbf'),
126 | binaryAjax(base + '.cpg')
127 | ]).then(function(args) {
128 | return parseDbf(args[0], args[1])
129 | })
130 | ]).then(shp.combine);
131 | }
132 | } else {
133 | return new Promise(function(resolve) {
134 | resolve(shp.parseZip(base));
135 | });
136 | }
137 | };
138 | shp.parseShp = function(shp, prj) {
139 | shp = toBuffer(shp);
140 | if (Buffer.isBuffer(prj)) {
141 | prj = prj.toString();
142 | }
143 | if (typeof prj === 'string') {
144 | prj = proj4(prj);
145 | return parseShp(shp, prj);
146 | } else {
147 | return parseShp(shp);
148 | }
149 | };
150 | shp.parseDbf = function(dbf, cpg) {
151 | dbf = toBuffer(dbf);
152 | return parseDbf(dbf, cpg);
153 | };
154 | module.exports = shp;
155 |
--------------------------------------------------------------------------------
/lib/parseShp.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | function isClockWise(array) {
4 | var sum = 0;
5 | var i = 1;
6 | var len = array.length;
7 | var prev, cur;
8 | while (i < len) {
9 | prev = cur || array[0];
10 | cur = array[i];
11 | sum += ((cur[0] - prev[0]) * (cur[1] + prev[1]));
12 | i++;
13 | }
14 | return sum > 0;
15 | }
16 |
17 | function polyReduce(a, b) {
18 | if (isClockWise(b) || !a.length) {
19 | a.push([b]);
20 | } else {
21 | a[a.length - 1].push(b);
22 | }
23 | return a;
24 | }
25 | ParseShp.prototype.parsePoint = function(data) {
26 | return {
27 | 'type': 'Point',
28 | 'coordinates': this.parseCoord(data, 0)
29 | };
30 | };
31 | ParseShp.prototype.parseZPoint = function(data) {
32 | var pointXY = this.parsePoint(data);
33 | pointXY.coordinates.push(this.parseCoord(data, 16));
34 | return pointXY;
35 | };
36 | ParseShp.prototype.parsePointArray = function(data, offset, num) {
37 | var out = [];
38 | var done = 0;
39 | while (done < num) {
40 | out.push(this.parseCoord(data, offset));
41 | offset += 16;
42 | done++;
43 | }
44 | return out;
45 | };
46 | ParseShp.prototype.parseZPointArray = function(data, zOffset, num, coordinates) {
47 | var i = 0;
48 | while (i < num) {
49 | coordinates[i].push(data.readDoubleLE(zOffset));
50 | i++;
51 | zOffset += 8;
52 | }
53 | return coordinates;
54 | };
55 | ParseShp.prototype.parseArrayGroup = function(data, offset, partOffset, num, tot) {
56 | var out = [];
57 | var done = 0;
58 | var curNum, nextNum = 0,
59 | pointNumber;
60 | while (done < num) {
61 | done++;
62 | partOffset += 4;
63 | curNum = nextNum;
64 | if (done === num) {
65 | nextNum = tot;
66 | } else {
67 | nextNum = data.readInt32LE(partOffset);
68 | }
69 | pointNumber = nextNum - curNum;
70 | if (!pointNumber) {
71 | continue;
72 | }
73 | out.push(this.parsePointArray(data, offset, pointNumber));
74 | offset += (pointNumber << 4);
75 | }
76 | return out;
77 | };
78 | ParseShp.prototype.parseZArrayGroup = function(data, zOffset, num, coordinates) {
79 | var i = 0;
80 | while (i < num) {
81 | coordinates[i] = this.parseZPointArray(data, zOffset, coordinates[i].length, coordinates[i]);
82 | zOffset += (coordinates[i].length << 3);
83 | i++;
84 | }
85 | return coordinates;
86 | };
87 | ParseShp.prototype.parseMultiPoint = function(data) {
88 | var out = {};
89 | var mins = this.parseCoord(data, 0);
90 | var maxs = this.parseCoord(data, 16);
91 | out.bbox = [
92 | mins[0],
93 | mins[1],
94 | maxs[0],
95 | maxs[1]
96 | ];
97 | var num = data.readInt32(32, true);
98 | var offset = 36;
99 | if (num === 1) {
100 | out.type = 'Point';
101 | out.coordinates = this.parseCoord(data, offset);
102 | } else {
103 | out.type = 'MultiPoint';
104 | out.coordinates = this.parsePointArray(data, offset, num);
105 | }
106 | return out;
107 | };
108 | ParseShp.prototype.parseZMultiPoint = function(data) {
109 | var geoJson = this.parseMultiPoint(data);
110 | var num;
111 | if (geoJson.type === 'Point') {
112 | geoJson.coordinates.push(data.readDoubleLE(72));
113 | return geoJson;
114 | } else {
115 | num = geoJson.coordinates.length;
116 | }
117 | var zOffset = 56 + (num << 4);
118 | geoJson.coordinates = this.parseZPointArray(data, zOffset, num, geoJson.coordinates);
119 | return geoJson;
120 | };
121 | ParseShp.prototype.parsePolyline = function(data) {
122 | var out = {};
123 | var mins = this.parseCoord(data, 0);
124 | var maxs = this.parseCoord(data, 16);
125 | out.bbox = [
126 | mins[0],
127 | mins[1],
128 | maxs[0],
129 | maxs[1]
130 | ];
131 | var numParts = data.readInt32LE(32);
132 | var num = data.readInt32LE(36);
133 | var offset, partOffset;
134 | if (numParts === 1) {
135 | out.type = 'LineString';
136 | offset = 44;
137 | out.coordinates = this.parsePointArray(data, offset, num);
138 | } else {
139 | out.type = 'MultiLineString';
140 | offset = 40 + (numParts << 2);
141 | partOffset = 40;
142 | out.coordinates = this.parseArrayGroup(data, offset, partOffset, numParts, num);
143 | }
144 | return out;
145 | };
146 | ParseShp.prototype.parseZPolyline = function(data) {
147 | var geoJson = this.parsePolyline(data);
148 | var num = geoJson.coordinates.length;
149 | var zOffset = 60 + (num << 4);
150 | if (geoJson.type === 'LineString') {
151 | geoJson.coordinates = this.parseZPointArray(data, zOffset, num, geoJson.coordinates);
152 | return geoJson;
153 | } else {
154 | geoJson.coordinates = this.parseZArrayGroup(data, zOffset, num, geoJson.coordinates);
155 | return geoJson;
156 | }
157 | };
158 | ParseShp.prototype.polyFuncs = function(out) {
159 | if (out.type === 'LineString') {
160 | out.type = 'Polygon';
161 | out.coordinates = [out.coordinates];
162 | return out;
163 | } else {
164 | out.coordinates = out.coordinates.reduce(polyReduce, []);
165 | if (out.coordinates.length === 1) {
166 | out.type = 'Polygon';
167 | out.coordinates = out.coordinates[0];
168 | return out;
169 | } else {
170 | out.type = 'MultiPolygon';
171 | return out;
172 | }
173 | }
174 | };
175 | ParseShp.prototype.parsePolygon = function(data) {
176 | return this.polyFuncs(this.parsePolyline(data));
177 | };
178 | ParseShp.prototype.parseZPolygon = function(data) {
179 | return this.polyFuncs(this.parseZPolyline(data));
180 | };
181 | var shpFuncObj = {
182 | 1: 'parsePoint',
183 | 3: 'parsePolyline',
184 | 5: 'parsePolygon',
185 | 8: 'parseMultiPoint',
186 | 11: 'parseZPoint',
187 | 13: 'parseZPolyline',
188 | 15: 'parseZPolygon',
189 | 18: 'parseZMultiPoint'
190 | };
191 |
192 |
193 |
194 | function makeParseCoord(trans) {
195 | if (trans) {
196 | return function(data, offset) {
197 | return trans.inverse([data.readDoubleLE(offset), data.readDoubleLE(offset + 8)]);
198 | };
199 | } else {
200 | return function(data, offset) {
201 | return [data.readDoubleLE(offset), data.readDoubleLE(offset + 8)];
202 | };
203 | }
204 | }
205 |
206 | function ParseShp(buffer, trans) {
207 | if (!(this instanceof ParseShp)) {
208 | return new ParseShp(buffer, trans);
209 | }
210 | this.buffer = buffer;
211 | this.shpFuncs(trans);
212 | this.rows = this.getRows();
213 | }
214 | ParseShp.prototype.shpFuncs = function(tran) {
215 | var num = this.getShpCode();
216 | if (num > 20) {
217 | num -= 20;
218 | }
219 | if (!(num in shpFuncObj)) {
220 | throw new Error('I don\'t know that shp type');
221 | }
222 | this.parseFunc = this[shpFuncObj[num]];
223 | this.parseCoord = makeParseCoord(tran);
224 | };
225 | ParseShp.prototype.getShpCode = function() {
226 | return this.parseHeader().shpCode;
227 | };
228 | ParseShp.prototype.parseHeader = function() {
229 | var view = this.buffer.slice(0, 100);
230 | return {
231 | length: view.readInt32BE(6 << 2),
232 | version: view.readInt32LE(7 << 2),
233 | shpCode: view.readInt32LE(8 << 2),
234 | bbox: [
235 | view.readDoubleLE(9 << 2),
236 | view.readDoubleLE(11 << 2),
237 | view.readDoubleLE(13 << 2),
238 | view.readDoubleLE(13 << 2)
239 | ]
240 | };
241 | };
242 | ParseShp.prototype.getRows = function() {
243 | var offset = 100;
244 | var len = this.buffer.byteLength;
245 | var out = [];
246 | var current;
247 | while (offset < len) {
248 | current = this.getRow(offset);
249 | offset += 8;
250 | offset += current.len;
251 | if (current.type) {
252 | out.push(this.parseFunc(current.data));
253 | }
254 | }
255 | return out;
256 | };
257 | ParseShp.prototype.getRow = function(offset) {
258 | var view = this.buffer.slice(offset, offset + 12);
259 | var len = view.readInt32BE(4) << 1;
260 | var data = this.buffer.slice(offset + 12, offset + len + 8);
261 |
262 | return {
263 | id: view.readInt32BE(0),
264 | len: len,
265 | data: data,
266 | type: view.readInt32LE(8)
267 | };
268 | };
269 | module.exports = function(buffer, trans) {
270 | return new ParseShp(buffer, trans).rows;
271 | };
272 |
--------------------------------------------------------------------------------
/lib/unzip.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | var JSZip = require('jszip');
4 | module.exports = function(buffer) {
5 | var zip = new JSZip(buffer);
6 | var files = zip.file(/.+/);
7 | var out = {};
8 | files.forEach(function(a) {
9 | if (a.name.slice(-3).toLowerCase() === 'shp' || a.name.slice(-3).toLowerCase() === 'dbf') {
10 | out[a.name] = a.asNodeBuffer();
11 | }
12 | else {
13 | out[a.name] = a.asText();
14 | }
15 | });
16 | return out;
17 | };
18 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "shpjs",
3 | "version": "3.4.0",
4 | "description": "A binary shapefile loader, for javascript. Not many caveats",
5 | "main": "lib/index.js",
6 | "repository": {
7 | "type": "git",
8 | "url": "git://github.com/calvinmetcalf/shapefile-js.git"
9 | },
10 | "scripts": {
11 | "test": "mocha ./test/test.js",
12 | "hint": "jshint ./lib/*.js",
13 | "build-test": "browserify ./test/test.js > ./test/bundle.js",
14 | "build": "browserify . -s shp > ./dist/shp.js",
15 | "min": "browserify . -s shp | uglifyjs -mc > ./dist/shp.min.js"
16 | },
17 | "author": "Calvin Metcalf",
18 | "license": "MIT",
19 | "readmeFilename": "README.md",
20 | "devDependencies": {
21 | "browserify": "^13.0.0",
22 | "chai": "^3.3.0",
23 | "chai-as-promised": "^5.1.0",
24 | "jszip": "^2.5.0",
25 | "mocha": "^2.3.3",
26 | "testling": "^1.6.1",
27 | "uglify-js": "^2.4.24",
28 | "uglifyjs": "^2.4.10"
29 | },
30 | "dependencies": {
31 | "jszip": "^2.4.0",
32 | "lie": "^3.0.1",
33 | "lru-cache": "^2.7.0",
34 | "parsedbf": "^1.0.0",
35 | "proj4": "^2.1.4"
36 | },
37 | "browser": {
38 | "./lib/binaryajax.js": "./lib/binaryajax-browser.js"
39 | }
40 | }
41 |
--------------------------------------------------------------------------------
/site/catiline.js:
--------------------------------------------------------------------------------
1 | /*! catiline 2.4.2 2013-08-08*/
2 | /*!©2013 Calvin Metcalf @license MIT https://github.com/calvinmetcalf/catiline */
3 | if (typeof document === 'undefined') {
4 | self._noTransferable=true;
5 | self.onmessage=function(e){
6 | /*jslint evil: true */
7 | eval(e.data);
8 | };
9 | } else {
10 | (function(global){
11 | 'use strict';
12 | /*!From setImmediate Copyright (c) 2012 Barnesandnoble.com,llc, Donavon West, and Domenic Denicola @license MIT https://github.com/NobleJS/setImmediate */
13 | (function(attachTo,global) {
14 | var tasks = (function () {
15 | function Task(handler, args) {
16 | this.handler = handler;
17 | this.args = args;
18 | }
19 | Task.prototype.run = function () {
20 | // See steps in section 5 of the spec.
21 | if (typeof this.handler === 'function') {
22 | // Choice of `thisArg` is not in the setImmediate spec; `undefined` is in the setTimeout spec though:
23 | // http://www.whatwg.org/specs/web-apps/current-work/multipage/timers.html
24 | this.handler.apply(undefined, this.args);
25 | } else {
26 | var scriptSource = '' + this.handler;
27 | /*jshint evil: true */
28 | eval(scriptSource);
29 | }
30 | };
31 |
32 | var nextHandle = 1; // Spec says greater than zero
33 | var tasksByHandle = {};
34 | var currentlyRunningATask = false;
35 |
36 | return {
37 | addFromSetImmediateArguments: function (args) {
38 | var handler = args[0];
39 | var argsToHandle = Array.prototype.slice.call(args, 1);
40 | var task = new Task(handler, argsToHandle);
41 |
42 | var thisHandle = nextHandle++;
43 | tasksByHandle[thisHandle] = task;
44 | return thisHandle;
45 | },
46 | runIfPresent: function (handle) {
47 | // From the spec: 'Wait until any invocations of this algorithm started before this one have completed.'
48 | // So if we're currently running a task, we'll need to delay this invocation.
49 | if (!currentlyRunningATask) {
50 | var task = tasksByHandle[handle];
51 | if (task) {
52 | currentlyRunningATask = true;
53 | try {
54 | task.run();
55 | } finally {
56 | delete tasksByHandle[handle];
57 | currentlyRunningATask = false;
58 | }
59 | }
60 | } else {
61 | // Delay by doing a setTimeout. setImmediate was tried instead, but in Firefox 7 it generated a
62 | // 'too much recursion' error.
63 | global.setTimeout(function () {
64 | tasks.runIfPresent(handle);
65 | }, 0);
66 | }
67 | },
68 | remove: function (handle) {
69 | delete tasksByHandle[handle];
70 | }
71 | };
72 | }());
73 | // Installs an event handler on `global` for the `message` event: see
74 | // * https://developer.mozilla.org/en/DOM/window.postMessage
75 | // * http://www.whatwg.org/specs/web-apps/current-work/multipage/comms.html#crossDocumentMessages
76 |
77 | var MESSAGE_PREFIX = 'com.catilinejs.setImmediate' + Math.random();
78 |
79 | function isStringAndStartsWith(string, putativeStart) {
80 | return typeof string === 'string' && string.substring(0, putativeStart.length) === putativeStart;
81 | }
82 |
83 | function onGlobalMessage(event) {
84 | // This will catch all incoming messages (even from other windows!), so we need to try reasonably hard to
85 | // avoid letting anyone else trick us into firing off. We test the origin is still this window, and that a
86 | // (randomly generated) unpredictable identifying prefix is present.
87 | if (event.source === global && isStringAndStartsWith(event.data, MESSAGE_PREFIX)) {
88 | var handle = event.data.substring(MESSAGE_PREFIX.length);
89 | tasks.runIfPresent(handle);
90 | }
91 | }
92 | if (global.addEventListener) {
93 | global.addEventListener('message', onGlobalMessage, false);
94 | } else {
95 | global.attachEvent('onmessage', onGlobalMessage);
96 | }
97 |
98 | attachTo.setImmediate = function () {
99 | var handle = tasks.addFromSetImmediateArguments(arguments);
100 |
101 | // Make `global` post a message to itself with the handle and identifying prefix, thus asynchronously
102 | // invoking our onGlobalMessage listener above.
103 | global.postMessage(MESSAGE_PREFIX + handle, '*');
104 |
105 | return handle;
106 | };
107 | })(catiline,global);
108 |
109 | /*! Promiscuous ©2013 Ruben Verborgh @license MIT https://github.com/RubenVerborgh/promiscuous*/
110 | (function (exports,tick) {
111 | var func = 'function';
112 | // Creates a deferred: an object with a promise and corresponding resolve/reject methods
113 | function Deferred() {
114 | // The `handler` variable points to the function that will
115 | // 1) handle a .then(onFulfilled, onRejected) call
116 | // 2) handle a .resolve or .reject call (if not fulfilled)
117 | // Before 2), `handler` holds a queue of callbacks.
118 | // After 2), `handler` is a simple .then handler.
119 | // We use only one function to save memory and complexity.
120 | var handler = function (onFulfilled, onRejected, value) {
121 | // Case 1) handle a .then(onFulfilled, onRejected) call
122 | var createdDeffered;
123 | if (onFulfilled !== handler) {
124 | createdDeffered = createDeferred();
125 | handler.queue.push({ deferred: createdDeffered, resolve: onFulfilled, reject: onRejected });
126 | return createdDeffered.promise;
127 | }
128 |
129 | // Case 2) handle a .resolve or .reject call
130 | // (`onFulfilled` acts as a sentinel)
131 | // The actual function signature is
132 | // .re[ject|solve](sentinel, success, value)
133 | var action = onRejected ? 'resolve' : 'reject',queue,deferred,callback;
134 | for (var i = 0, l = handler.queue.length; i < l; i++) {
135 | queue = handler.queue[i];
136 | deferred = queue.deferred;
137 | callback = queue[action];
138 | if (typeof callback !== func) {
139 | deferred[action](value);
140 | } else {
141 | execute(callback, value, deferred);
142 | }
143 | }
144 | // Replace this handler with a simple resolved or rejected handler
145 | handler = createHandler(promise, value, onRejected);
146 | };
147 | function Promise(){
148 | this.then=function (onFulfilled, onRejected) {
149 | return handler(onFulfilled, onRejected);
150 | };
151 | }
152 | var promise = new Promise();
153 | this.promise = promise;
154 | // The queue of deferreds
155 | handler.queue = [];
156 |
157 | this.resolve = function (value) {
158 | handler.queue && handler(handler, true, value);
159 | };
160 |
161 | this.reject = function (reason) {
162 | handler.queue && handler(handler, false, reason);
163 | };
164 | }
165 |
166 | function createDeferred(){
167 | return new Deferred();
168 | }
169 |
170 | // Creates a fulfilled or rejected .then function
171 | function createHandler(promise, value, success) {
172 | return function (onFulfilled, onRejected) {
173 | var callback = success ? onFulfilled : onRejected, result;
174 | if (typeof callback !== func) {
175 | return promise;
176 | }
177 | execute(callback, value, result = createDeferred());
178 | return result.promise;
179 | };
180 | }
181 |
182 | // Executes the callback with the specified value,
183 | // resolving or rejecting the deferred
184 | function execute(callback, value, deferred) {
185 | tick(function () {
186 | var result;
187 | try {
188 | result = callback(value);
189 | if (result && typeof result.then === func) {
190 | result.then(deferred.resolve, deferred.reject);
191 | } else {
192 | deferred.resolve(result);
193 | }
194 | }
195 | catch (error) {
196 | deferred.reject(error);
197 | }
198 | });
199 | }
200 |
201 | // Returns a resolved promise
202 | exports.resolve= function (value) {
203 | var promise = {};
204 | promise.then = createHandler(promise, value, true);
205 | return promise;
206 | };
207 | // Returns a rejected promise
208 | exports.reject= function (reason) {
209 | var promise = {};
210 | promise.then = createHandler(promise, reason, false);
211 | return promise;
212 | };
213 | // Returns a deferred
214 | exports.deferred= createDeferred;
215 | exports.all=function(array){
216 | var promise = exports.deferred();
217 | var len = array.length;
218 | var resolved=0;
219 | var out = [];
220 | var onSuccess=function(n){
221 | return function(v){
222 | out[n]=v;
223 | resolved++;
224 | if(resolved===len){
225 | promise.resolve(out);
226 | }
227 | };
228 | };
229 | array.forEach(function(v,i){
230 | v.then(onSuccess(i),function(a){
231 | promise.reject(a);
232 | });
233 | });
234 | return promise.promise;
235 | };
236 | })(catiline,catiline.setImmediate);
237 |
238 | catiline._hasWorker = typeof Worker !== 'undefined'&&typeof fakeLegacy === 'undefined';
239 | catiline.URL = window.URL || window.webkitURL;
240 | catiline._noTransferable=!catiline.URL;
241 | //regex out the importScript call and move it up to the top out of the function.
242 | function regexImports(string){
243 | var rest=string,
244 | match = true,
245 | matches = {},
246 | loopFunc = function(a,b){
247 | if(b){
248 | 'importScripts('+b.split(',').forEach(function(cc){
249 | matches[catiline.makeUrl(cc.match(/\s*[\'\"](\S*)[\'\"]\s*/)[1])]=true; // trim whitespace, add to matches
250 | })+');\n';
251 | }
252 | };
253 | while(match){
254 | match = rest.match(/(importScripts\(.*?\);?)/);
255 | rest = rest.replace(/(importScripts\(\s*(?:[\'\"].*?[\'\"])?\s*\);?)/,'\n');
256 | if(match){
257 | match[0].replace(/importScripts\(\s*([\'\"].*?[\'\"])?\s*\);?/g,loopFunc);
258 | }
259 | }
260 | matches = Object.keys(matches);
261 | return [matches,rest];
262 | }
263 |
264 | function moveImports(string){
265 | var str = regexImports(string);
266 | var matches = str[0];
267 | var rest = str[1];
268 | if(matches.length>0){
269 | return 'importScripts(\''+matches.join('\',\'')+'\');\n'+rest;
270 | }else{
271 | return rest;
272 | }
273 | }
274 | function moveIimports(string){
275 | var str = regexImports(string);
276 | var matches = str[0];
277 | var rest = str[1];
278 | if(matches.length>0){
279 | return 'importScripts(\''+matches.join('\',\'')+'\');eval(__scripts__);\n'+rest;
280 | }else{
281 | return rest;
282 | }
283 | }
284 | function getPath(){
285 | if(typeof SHIM_WORKER_PATH !== 'undefined'){
286 | return SHIM_WORKER_PATH;
287 | }else if('SHIM_WORKER_PATH' in catiline){
288 | return catiline.SHIM_WORKER_PATH;
289 | }
290 | var scripts = document.getElementsByTagName('script');
291 | var len = scripts.length;
292 | var i = 0;
293 | while(i0){',
328 | ' scripts.forEach(function(url){',
329 | ' var ajax = new XMLHttpRequest();',
330 | ' ajax.open(\'GET\',url,false);',
331 | ' ajax.send();__scripts__+=ajax.responseText;',
332 | ' __scripts__+=\'\\n;\';',
333 | ' });',
334 | ' }',
335 | '};',
336 | script,
337 | '}catch(e){',
338 | ' window.parent.postMessage([\''+codeword+'\',\'error\'],\'*\')',
339 | '}'].join('\n');
340 | appendScript(iDoc,text);
341 |
342 | return iFrame;
343 | }
344 | function makeIframe(script,codeword){
345 | var promise = catiline.deferred();
346 | if(document.readyState==='complete'){
347 | promise.resolve(actualMakeI(script,codeword));
348 | }else{
349 | window.addEventListener('load',function(){
350 | promise.resolve(actualMakeI(script,codeword));
351 | },false);
352 | }
353 | return promise.promise;
354 | }
355 | catiline.makeIWorker = function (strings,codeword){
356 | var script =moveIimports(strings.join(''));
357 | var worker = {onmessage:function(){}};
358 | var ipromise = makeIframe(script,codeword);
359 | window.addEventListener('message',function(e){
360 | if(typeof e.data ==='string'&&e.data.length>codeword.length&&e.data.slice(0,codeword.length)===codeword){
361 | worker.onmessage({data:JSON.parse(e.data.slice(codeword.length))});
362 | }
363 | });
364 | worker.postMessage=function(data){
365 | ipromise.then(function(iFrame){
366 | iFrame.contentWindow.postMessage(JSON.stringify(data),'*');
367 | });
368 | };
369 | worker.terminate=function(){
370 | ipromise.then(function(iFrame){
371 | document.body.removeChild(iFrame);
372 | });
373 | };
374 | return worker;
375 |
376 | };
377 | //accepts an array of strings, joins them, and turns them into a worker.
378 | function makeFallbackWorker(script){
379 | catiline._noTransferable=true;
380 | var worker = new Worker(getPath());
381 | worker.postMessage(script);
382 | return worker;
383 | }
384 | catiline.makeWorker = function (strings, codeword){
385 | if(!catiline._hasWorker){
386 | return catiline.makeIWorker(strings,codeword);
387 | }
388 | var worker;
389 | var script =moveImports(strings.join(''));
390 | if(catiline._noTransferable){
391 | return makeFallbackWorker(script);
392 | }
393 | try{
394 | worker= new Worker(catiline.URL.createObjectURL(new Blob([script],{type: 'text/javascript'})));
395 | }catch(e){
396 | try{
397 | worker=makeFallbackWorker(script);
398 | }catch(ee){
399 | worker = catiline.makeIWorker(strings,codeword);
400 | }
401 | }finally{
402 | return worker;
403 | }
404 | };
405 |
406 | catiline.makeUrl = function (fileName) {
407 | var link = document.createElement('link');
408 | link.href = fileName;
409 | return link.href;
410 | };
411 |
412 | catiline.Worker = function Catiline(obj) {
413 | if(typeof obj === 'function'){
414 | obj = {
415 | data:obj
416 | };
417 | }
418 | var __codeWord__='com.catilinejs.'+(catiline._hasWorker?'iframe':'worker')+Math.random();
419 | var listeners = {};
420 | var self = this;
421 | self.on = function (eventName, func, scope) {
422 | scope = scope || self;
423 | if (eventName.indexOf(' ') > 0) {
424 | eventName.split(' ').map(function (v) {
425 | return self.on(v, func, scope);
426 | }, this);
427 | return self;
428 | }
429 | if (!(eventName in listeners)) {
430 | listeners[eventName] = [];
431 | }
432 | listeners[eventName].push(function (a) {
433 | func.call(scope, a);
434 | });
435 | return self;
436 | };
437 |
438 | function _fire(eventName, data) {
439 | if (eventName.indexOf(' ') > 0) {
440 | eventName.split(' ').forEach(function (v) {
441 | _fire(v, data);
442 | });
443 | return self;
444 | }
445 | if (!(eventName in listeners)) {
446 | return self;
447 | }
448 | listeners[eventName].forEach(function (v) {
449 | v(data);
450 | });
451 | return self;
452 | }
453 | self.fire = function (eventName, data, transfer) {
454 | if(catiline._noTransferable){
455 | worker.postMessage([[eventName], data]);
456 | }else{
457 | worker.postMessage([[eventName], data], transfer);
458 | }
459 |
460 | return self;
461 | };
462 | self.off = function (eventName, func) {
463 | if (eventName.indexOf(' ') > 0) {
464 | eventName.split(' ').map(function (v) {
465 | return self.off(v, func);
466 | });
467 | return self;
468 | }
469 | if (!(eventName in listeners)) {
470 | return self;
471 | }
472 | else if (!func) {
473 | delete listeners[eventName];
474 | }
475 | else {
476 | if (listeners[eventName].indexOf(func) > -1) {
477 | if (listeners[eventName].length > 1) {
478 | delete listeners[eventName];
479 | }
480 | else {
481 | listeners[eventName].splice(listeners[eventName].indexOf(func), 1);
482 | }
483 | }
484 | }
485 | return self;
486 | };
487 | var i = 0;
488 | var promises = [];
489 | var rejectPromises = function (msg) {
490 | if (typeof msg !== 'string' && 'preventDefault' in msg) {
491 | msg.preventDefault();
492 | msg = msg.message;
493 | }
494 | promises.forEach(function (p) {
495 | if (p) {
496 | p.reject(msg);
497 | }
498 | });
499 | };
500 | obj.__codeWord__='"'+__codeWord__+'"';
501 | if (!('initialize' in obj)) {
502 | if ('init' in obj) {
503 | obj.initialize = obj.init;
504 | }
505 | else {
506 | obj.initialize = function () {};
507 | }
508 | }
509 | var fObj = '{\n\t';
510 | var keyFunc = function (key) {
511 | var out = function (data, transfer) {
512 | var i = promises.length;
513 | promises[i] = catiline.deferred();
514 | if(catiline._noTransferable){
515 | worker.postMessage([[__codeWord__, i], key, data]);
516 | }else{
517 | worker.postMessage([[__codeWord__, i], key, data], transfer);
518 | }
519 | return promises[i].promise;
520 | };
521 | return out;
522 | };
523 | for (var key in obj) {
524 | if (i !== 0) {
525 | fObj = fObj + ',\n\t';
526 | }
527 | else {
528 | i++;
529 | }
530 | fObj = fObj + key + ':' + obj[key].toString();
531 | self[key] = keyFunc(key);
532 | }
533 | fObj = fObj + '}';
534 | var worker = catiline.makeWorker(['\'use strict\';\n\nvar _db = ',fObj,';\nvar listeners = {};\nvar __iFrame__ = typeof document!=="undefined";\nvar __self__={onmessage:function(e){\n _fire("messege",e.data[1]);\n if(e.data[0][0]===_db.__codeWord__){\n return regMsg(e);\n }else{\n _fire(e.data[0][0],e.data[1]);\n }\n}};\nif(__iFrame__){\n window.onmessage=function(e){\n if(typeof e.data === "string"){\n e ={data: JSON.parse(e.data)};\n }\n __self__.onmessage(e);\n };\n}else{\n self.onmessage=__self__.onmessage;\n}\n__self__.postMessage=function(rawData, transfer){\n var data;\n if(!self._noTransferable&&!__iFrame__){\n self.postMessage(rawData, transfer);\n }else if(__iFrame__){\n data = _db.__codeWord__+JSON.stringify(rawData);\n window.parent.postMessage(data,"*");\n }else if(self._noTransferable){\n self.postMessage(rawData);\n }\n};\n_db.on = function (eventName, func, scope) {\n if(eventName.indexOf(" ")>0){\n return eventName.split(" ").map(function(v){\n return _db.on(v,func,scope);\n },_db);\n }\n scope = scope || _db;\n if (!(eventName in listeners)) {\n listeners[eventName] = [];\n }\n listeners[eventName].push(function (a) {\n func.call(scope, a, _db);\n });\n};\nfunction _fire(eventName,data){\n if(eventName.indexOf(" ")>0){\n eventName.split(" ").forEach(function(v){\n _fire(v,data);\n });\n return;\n }\n if (!(eventName in listeners)) {\n return;\n }\n listeners[eventName].forEach(function (v) {\n v(data);\n });\n}\n\n_db.fire = function (eventName, data, transfer) {\n __self__.postMessage([[eventName], data], transfer);\n};\n_db.off=function(eventName,func){\n if(eventName.indexOf(" ")>0){\n return eventName.split(" ").map(function(v){\n return _db.off(v,func);\n });\n }\n if(!(eventName in listeners)){\n return;\n }else if(!func){\n delete listeners[eventName];\n }else{\n if(listeners[eventName].indexOf(func)>-1){\n if(listeners[eventName].length>1){\n delete listeners[eventName];\n }else{\n listeners[eventName].splice(listeners[eventName].indexOf(func),1);\n }\n }\n }\n};\nvar console={};\nfunction makeConsole(method){\n return function(){\n var len = arguments.length;\n var out =[];\n var i = 0;\n while (if)return a;e.splice(f,d);return e.concat(c||[]).join("/")}return c}function H(a){var b=a.indexOf("!");return{g:a.substr(b+1),d:0<=b&&a.substr(0,b)}}function M(){}function u(a,b){M.prototype=
4 | a||N;var d=new M;M.prototype=N;for(var c in b)d[c]=b[c];return d}function A(){function a(a,b,d){c.push([a,b,d])}function b(a,b){for(var d,e=0;d=c[e++];)(d=d[a])&&d(b)}var d,c,e;d=this;c=[];e=function(d,g){a=d?function(a){a&&a(g)}:function(a,b){b&&b(g)};e=R;b(d?0:1,g);b=R;c=k};this.A=function(b,c,e){a(b,c,e);return d};this.h=function(a){d.oa=a;e(!0,a)};this.e=function(a){d.na=a;e(!1,a)};this.u=function(a){b(2,a)}}function I(a){return a instanceof A||a instanceof y}function v(a,b,d,c){I(a)?a.A(b,d,
5 | c):b(a)}function B(a,b,d){var c;return function(){0<=--a&&b&&(c=b.apply(k,arguments));0==a&&d&&d(c);return c}}function z(){var a,b;a=[].slice.call(arguments);m(a[0],"Object")&&(b=a.shift(),b=J(b));return new y(a[0],a[1],a[2],b)}function J(a,b,d){var c,e,f;if(a&&(h.O(a),n=h.a(a),"preloads"in a&&(c=new y(a.preloads,k,d,C,!0),h.K(function(){C=c})),f=(f=a.main)&&String(f).split(Z)))return e=new A,e.A(b,d),a=f[1]?function(){new y([f[1]],e.h,e.e)}:e.e,new y([f[0]],e.h,a),e}function y(a,b,d,c,e){var f;f=
6 | h.j(n,k,[].concat(a),e);this.then=this.A=a=function(a,b){v(f,function(b){a&&a.apply(k,b)},function(a){if(b)b(a);else throw a;});return this};this.next=function(a,b,c){return new y(a,b,c,f)};this.config=J;(b||d)&&a(b,d);h.K(function(){v(e||C,function(){v(c,function(){h.q(f)},d)})})}function T(a){var b,d;b=a.id;b==k&&(D!==k?D={G:"Multiple anonymous defines encountered"}:(b=h.$())||(D=a));if(b!=k){d=l[b];b in l||(d=h.i(b,n),d=h.C(d.a,b),l[b]=d);if(!I(d))throw Error("duplicate define: "+b);d.ca=!1;h.D(d,
7 | a)}}function O(){var a=h.X(arguments);T(a)}var n,w,E,x=p.document,P=x&&(x.head||x.getElementsByTagName("head")[0]),$=P&&P.getElementsByTagName("base")[0]||null,U={},V={},K={},aa="addEventListener"in p?{}:{loaded:1,complete:1},N={},X=N.toString,k,l={},L={},C=!1,D,W=/^\/|^[^:]+:\/\//,Y=/(\.)(\.?)(?:$|\/([^\.\/]+.*)?)/g,ba=/\/\*[\s\S]*?\*\/|\/\/.*?[\n\r]/g,ca=/require\s*\(\s*(["'])(.*?[^\\])\1\s*\)|[^\\]?(["'])/g,Z=/\s*,\s*/,Q,h;h={m:function(a,b,d){var c;a=S(a,b);if("."==a.charAt(0))return a;c=H(a);
8 | a=(b=c.d)||c.g;a in d.c&&(a=d.c[a].l||a);b&&(0>b.indexOf("/")&&!(b in d.c)&&(a=G(d.M)+"/"+b),a=a+"!"+c.g);return a},j:function(a,b,d,c){function e(b,c){var d,f;d=h.m(b,g.id,a);if(!c)return d;f=H(d);if(!f.d)return d;d=l[f.d];f.g="normalize"in d?d.normalize(f.g,e,g.a)||"":e(f.g);return f.d+"!"+f.g}function f(b,d,f){var r;r=d&&function(a){d.apply(k,a)};if(m(b,"String")){if(r)throw Error("require(id, callback) not allowed");f=e(b,!0);b=l[f];if(!(f in l))throw Error("Module not resolved: "+f);return(f=
9 | I(b)&&b.b)||b}v(h.q(h.j(a,g.id,b,c)),r,f)}var g;g=new A;g.id=b||"";g.aa=c;g.F=d;g.a=a;g.v=f;f.toUrl=function(b){return h.i(e(b,!0),a).url};g.m=e;return g},C:function(a,b,d){var c,e,f;c=h.j(a,b,k,d);e=c.h;f=B(1,function(a){c.p=a;try{return h.R(c)}catch(b){c.e(b)}});c.h=function(a){v(d||C,function(){e(l[c.id]=L[c.url]=f(a))})};c.H=function(a){v(d||C,function(){c.b&&(f(a),c.u(V))})};return c},Q:function(a,b,d,c){return h.j(a,d,k,c)},Z:function(a){return a.v},I:function(a){return a.b||(a.b={})},Y:function(a){var b=
10 | a.r;b||(b=a.r={id:a.id,uri:h.J(a),exports:h.I(a),config:function(){return a.a}},b.b=b.exports);return b},J:function(a){return a.url||(a.url=h.B(a.v.toUrl(a.id),a.a))},O:function(a){var b,d,c,e,f;b="curl";d="define";c=e=p;if(a&&(f=a.overwriteApi||a.la,b=a.apiName||a.ea||b,c=a.apiContext||a.da||c,d=a.defineName||a.ga||d,e=a.defineContext||a.fa||e,w&&m(w,"Function")&&(p.curl=w),w=null,E&&m(E,"Function")&&(p.define=E),E=null,!f)){if(c[b]&&c[b]!=z)throw Error(b+" already exists");if(e[d]&&e[d]!=O)throw Error(d+
11 | " already exists");}c[b]=z;e[d]=O},a:function(a){function b(a,b){var d,c,g,q,s;for(s in a){g=a[s];m(g,"String")&&(g={path:a[s]});g.name=g.name||s;q=e;c=H(G(g.name));d=c.g;if(c=c.d)q=f[c],q||(q=f[c]=u(e),q.c=u(e.c),q.f=[]),delete a[s];c=g;var l=b,F=void 0;c.path=G(c.path||c.location||"");l&&(F=c.main||"./main","."==F.charAt(0)||(F="./"+F),c.l=S(F,c.name+"/"));c.a=c.config;c.a&&(c.a=u(e,c.a));c.P=d.split("/").length;d?(q.c[d]=c,q.f.push(d)):q.n=h.N(g.path,e)}}function d(a){var b=a.c;a.L=RegExp("^("+
12 | a.f.sort(function(a,c){return b[c].P-b[a].P}).join("|").replace(/\/|\./g,"\\$&")+")(?=\\/|$)");delete a.f}var c,e,f,g;"baseUrl"in a&&(a.n=a.baseUrl);"main"in a&&(a.l=a.main);"preloads"in a&&(a.ma=a.preloads);"pluginPath"in a&&(a.M=a.pluginPath);if("dontAddFileExt"in a||a.k)a.k=RegExp(a.dontAddFileExt||a.k);c=n;e=u(c,a);e.c=u(c.c);f=a.plugins||{};e.plugins=u(c.plugins);e.t=u(c.t,a.t);e.s=u(c.s,a.s);e.f=[];b(a.packages,!0);b(a.paths,!1);for(g in f)a=h.m(g+"!","",e),e.plugins[a.substr(0,a.length-1)]=
13 | f[g];f=e.plugins;for(g in f)if(f[g]=u(e,f[g]),a=f[g].f)f[g].f=a.concat(e.f),d(f[g]);for(g in c.c)e.c.hasOwnProperty(g)||e.f.push(g);d(e);return e},i:function(a,b){var d,c,e,f;d=b.c;e=W.test(a)?a:a.replace(b.L,function(a){c=d[a]||{};f=c.a;return c.path||""});return{a:f||n,url:h.N(e,b)}},N:function(a,b){var d=b.n;return d&&!W.test(a)?G(d)+"/"+a:a},B:function(a,b){return a+((b||n).k.test(a)?"":".js")},ba:function(a,b,d){var c=x.createElement("script");c.onload=c.onreadystatechange=function(d){d=d||p.event;
14 | if("load"==d.type||aa[c.readyState])delete K[a.id],c.onload=c.onreadystatechange=c.onerror="",b()};c.onerror=function(){d(Error("Syntax or http error: "+a.url))};c.type=a.ia||"text/javascript";c.charset="utf-8";c.async=!a.ka;c.src=a.url;K[a.id]=c;P.insertBefore(c,$);return c},S:function(a){var b=[],d;("string"==typeof a?a:a.toSource?a.toSource():a.toString()).replace(ba,"").replace(ca,function(a,e,f,g){g?d=d==g?k:d:d||b.push(f);return""});return b},X:function(a){var b,d,c,e,f,g;f=a.length;c=a[f-1];
15 | e=m(c,"Function")?c.length:-1;2==f?m(a[0],"Array")?d=a[0]:b=a[0]:3==f&&(b=a[0],d=a[1]);!d&&0
2 |
3 |
8 | Example
9 |
10 |
11 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
--------------------------------------------------------------------------------
/site/proj-small.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Projected Shapefiles in Leaflet!
9 |
10 |
13 |
14 |
15 |
20 |
21 |
51 |
52 |
--------------------------------------------------------------------------------
/site/proj.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Projected Shapefiles in Leaflet!
9 |
10 |
13 |
14 |
15 |
20 |
21 |
55 |
56 |
--------------------------------------------------------------------------------
/site/require.js:
--------------------------------------------------------------------------------
1 | /*
2 | RequireJS 2.1.8 Copyright (c) 2010-2012, The Dojo Foundation All Rights Reserved.
3 | Available via the MIT or new BSD license.
4 | see: http://github.com/jrburke/requirejs for details
5 | */
6 | var requirejs,require,define;
7 | (function(Z){function H(b){return"[object Function]"===L.call(b)}function I(b){return"[object Array]"===L.call(b)}function y(b,c){if(b){var d;for(d=0;dthis.depCount&&!this.defined){if(H(m)){if(this.events.error&&this.map.isDefine||j.onError!==aa)try{e=i.execCb(c,m,b,e)}catch(d){a=d}else e=i.execCb(c,m,b,e);this.map.isDefine&&((b=this.module)&&void 0!==b.exports&&b.exports!==
19 | this.exports?e=b.exports:void 0===e&&this.usingExports&&(e=this.exports));if(a)return a.requireMap=this.map,a.requireModules=this.map.isDefine?[this.map.id]:null,a.requireType=this.map.isDefine?"define":"require",v(this.error=a)}else e=m;this.exports=e;if(this.map.isDefine&&!this.ignore&&(r[c]=e,j.onResourceLoad))j.onResourceLoad(i,this.map,this.depMaps);x(c);this.defined=!0}this.defining=!1;this.defined&&!this.defineEmitted&&(this.defineEmitted=!0,this.emit("defined",this.exports),this.defineEmitComplete=
20 | !0)}}else this.fetch()}},callPlugin:function(){var a=this.map,b=a.id,d=n(a.prefix);this.depMaps.push(d);t(d,"defined",u(this,function(e){var m,d;d=this.map.name;var g=this.map.parentMap?this.map.parentMap.name:null,h=i.makeRequire(a.parentMap,{enableBuildCallback:!0});if(this.map.unnormalized){if(e.normalize&&(d=e.normalize(d,function(a){return c(a,g,!0)})||""),e=n(a.prefix+"!"+d,this.map.parentMap),t(e,"defined",u(this,function(a){this.init([],function(){return a},null,{enabled:!0,ignore:!0})})),
21 | d=l(p,e.id)){this.depMaps.push(e);if(this.events.error)d.on("error",u(this,function(a){this.emit("error",a)}));d.enable()}}else m=u(this,function(a){this.init([],function(){return a},null,{enabled:!0})}),m.error=u(this,function(a){this.inited=!0;this.error=a;a.requireModules=[b];F(p,function(a){0===a.map.id.indexOf(b+"_unnormalized")&&x(a.map.id)});v(a)}),m.fromText=u(this,function(e,c){var d=a.name,g=n(d),B=O;c&&(e=c);B&&(O=!1);q(g);s(k.config,b)&&(k.config[d]=k.config[b]);try{j.exec(e)}catch(ca){return v(A("fromtexteval",
22 | "fromText eval for "+b+" failed: "+ca,ca,[b]))}B&&(O=!0);this.depMaps.push(g);i.completeLoad(d);h([d],m)}),e.load(a.name,h,m,k)}));i.enable(d,this);this.pluginMaps[d.id]=d},enable:function(){T[this.map.id]=this;this.enabling=this.enabled=!0;y(this.depMaps,u(this,function(a,b){var c,e;if("string"===typeof a){a=n(a,this.map.isDefine?this.map:this.map.parentMap,!1,!this.skipMap);this.depMaps[b]=a;if(c=l(N,a.id)){this.depExports[b]=c(this);return}this.depCount+=1;t(a,"defined",u(this,function(a){this.defineDep(b,
23 | a);this.check()}));this.errback&&t(a,"error",u(this,this.errback))}c=a.id;e=p[c];!s(N,c)&&(e&&!e.enabled)&&i.enable(a,this)}));F(this.pluginMaps,u(this,function(a){var b=l(p,a.id);b&&!b.enabled&&i.enable(a,this)}));this.enabling=!1;this.check()},on:function(a,b){var c=this.events[a];c||(c=this.events[a]=[]);c.push(b)},emit:function(a,b){y(this.events[a],function(a){a(b)});"error"===a&&delete this.events[a]}};i={config:k,contextName:b,registry:p,defined:r,urlFetched:S,defQueue:G,Module:X,makeModuleMap:n,
24 | nextTick:j.nextTick,onError:v,configure:function(a){a.baseUrl&&"/"!==a.baseUrl.charAt(a.baseUrl.length-1)&&(a.baseUrl+="/");var b=k.pkgs,c=k.shim,e={paths:!0,config:!0,map:!0};F(a,function(a,b){e[b]?"map"===b?(k.map||(k.map={}),Q(k[b],a,!0,!0)):Q(k[b],a,!0):k[b]=a});a.shim&&(F(a.shim,function(a,b){I(a)&&(a={deps:a});if((a.exports||a.init)&&!a.exportsFn)a.exportsFn=i.makeShimExports(a);c[b]=a}),k.shim=c);a.packages&&(y(a.packages,function(a){a="string"===typeof a?{name:a}:a;b[a.name]={name:a.name,
25 | location:a.location||a.name,main:(a.main||"main").replace(ja,"").replace(ea,"")}}),k.pkgs=b);F(p,function(a,b){!a.inited&&!a.map.unnormalized&&(a.map=n(b))});if(a.deps||a.callback)i.require(a.deps||[],a.callback)},makeShimExports:function(a){return function(){var b;a.init&&(b=a.init.apply(Z,arguments));return b||a.exports&&ba(a.exports)}},makeRequire:function(a,f){function d(e,c,h){var g,k;f.enableBuildCallback&&(c&&H(c))&&(c.__requireJsBuild=!0);if("string"===typeof e){if(H(c))return v(A("requireargs",
26 | "Invalid require call"),h);if(a&&s(N,e))return N[e](p[a.id]);if(j.get)return j.get(i,e,a,d);g=n(e,a,!1,!0);g=g.id;return!s(r,g)?v(A("notloaded",'Module name "'+g+'" has not been loaded yet for context: '+b+(a?"":". Use require([])"))):r[g]}K();i.nextTick(function(){K();k=q(n(null,a));k.skipMap=f.skipMap;k.init(e,c,h,{enabled:!0});C()});return d}f=f||{};Q(d,{isBrowser:z,toUrl:function(b){var d,f=b.lastIndexOf("."),g=b.split("/")[0];if(-1!==f&&(!("."===g||".."===g)||1h.attachEvent.toString().indexOf("[native code"))&&!W?(O=!0,h.attachEvent("onreadystatechange",b.onScriptLoad)):(h.addEventListener("load",b.onScriptLoad,!1),h.addEventListener("error",
34 | b.onScriptError,!1)),h.src=d,K=h,C?x.insertBefore(h,C):x.appendChild(h),K=null,h;if(da)try{importScripts(d),b.completeLoad(c)}catch(l){b.onError(A("importscripts","importScripts failed for "+c+" at "+d,l,[c]))}};z&&M(document.getElementsByTagName("script"),function(b){x||(x=b.parentNode);if(J=b.getAttribute("data-main"))return q=J,t.baseUrl||(D=q.split("/"),q=D.pop(),fa=D.length?D.join("/")+"/":"./",t.baseUrl=fa),q=q.replace(ea,""),j.jsExtRegExp.test(q)&&(q=J),t.deps=t.deps?t.deps.concat(q):[q],!0});
35 | define=function(b,c,d){var h,j;"string"!==typeof b&&(d=c,c=b,b=null);I(c)||(d=c,c=null);!c&&H(d)&&(c=[],d.length&&(d.toString().replace(la,"").replace(ma,function(b,d){c.push(d)}),c=(1===d.length?["require"]:["require","exports","module"]).concat(c)));if(O){if(!(h=K))P&&"interactive"===P.readyState||M(document.getElementsByTagName("script"),function(b){if("interactive"===b.readyState)return P=b}),h=P;h&&(b||(b=h.getAttribute("data-requiremodule")),j=E[h.getAttribute("data-requirecontext")])}(j?j.defQueue:
36 | R).push([b,c,d])};define.amd={jQuery:!0};j.exec=function(b){return eval(b)};j(t)}})(this);
37 |
--------------------------------------------------------------------------------
/test/data/bad.dbf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/bad.dbf
--------------------------------------------------------------------------------
/test/data/bad.shp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/bad.shp
--------------------------------------------------------------------------------
/test/data/badzip.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/badzip.zip
--------------------------------------------------------------------------------
/test/data/codepage.cpg:
--------------------------------------------------------------------------------
1 | ASNI 1250
2 |
--------------------------------------------------------------------------------
/test/data/codepage.dbf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/codepage.dbf
--------------------------------------------------------------------------------
/test/data/codepage.prj:
--------------------------------------------------------------------------------
1 | GEOGCS["GCS_WGS_1984",DATUM["D_WGS_1984",SPHEROID["WGS_1984",6378137,298.257223563]],PRIMEM["Greenwich",0],UNIT["Degree",0.017453292519943295]]
--------------------------------------------------------------------------------
/test/data/codepage.qpj:
--------------------------------------------------------------------------------
1 | GEOGCS["WGS 84",DATUM["WGS_1984",SPHEROID["WGS 84",6378137,298.257223563,AUTHORITY["EPSG","7030"]],AUTHORITY["EPSG","6326"]],PRIMEM["Greenwich",0,AUTHORITY["EPSG","8901"]],UNIT["degree",0.0174532925199433,AUTHORITY["EPSG","9122"]],AUTHORITY["EPSG","4326"]]
2 |
--------------------------------------------------------------------------------
/test/data/codepage.shp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/codepage.shp
--------------------------------------------------------------------------------
/test/data/codepage.shx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/codepage.shx
--------------------------------------------------------------------------------
/test/data/codepage.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/codepage.zip
--------------------------------------------------------------------------------
/test/data/counties.dbf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/counties.dbf
--------------------------------------------------------------------------------
/test/data/counties.sbn:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/counties.sbn
--------------------------------------------------------------------------------
/test/data/counties.sbx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/counties.sbx
--------------------------------------------------------------------------------
/test/data/counties.shp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/counties.shp
--------------------------------------------------------------------------------
/test/data/counties.shp.xml:
--------------------------------------------------------------------------------
1 | 20130910 08255500 FALSE CreateFeatureclass "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries" Towns # GISPLANNER_Layer SAME_AS_TEMPLATE SAME_AS_TEMPLATE "PROJCS['NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001',GEOGCS['GCS_North_American_1983',DATUM['D_North_American_1983',SPHEROID['GRS_1980',6378137.0,298.257222101]],PRIMEM['Greenwich',0.0],UNIT['Degree',0.0174532925199433]],PROJECTION['Lambert_Conformal_Conic'],PARAMETER['False_Easting',200000.0],PARAMETER['False_Northing',750000.0],PARAMETER['Central_Meridian',-71.5],PARAMETER['Standard_Parallel_1',41.71666666666667],PARAMETER['Standard_Parallel_2',42.68333333333333],PARAMETER['Latitude_Of_Origin',41.0],UNIT['Meter',1.0]];-361489.141077092 327975.618391579 1953.12499818101;0 1;0 1" # 0 0 0 "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisVector.GISADMIN.Towns" Append GISPLANNER_Layer "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisVector.GISADMIN.Towns" TEST "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisVector.GISADMIN.Towns" FeatureClassToFeatureClass "Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Mark\gisdevelopment.GISPLANNER.boundary" "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries" Towns # "TOWN TOWN VISIBLE;TOWN_ID TOWN_ID VISIBLE;TOWNS_ID TOWNS_ID VISIBLE;COASTAL_POLY COASTAL_POLY VISIBLE;SQUARE_MILES SQUARE_MILES VISIBLE;SHAPE.area SHAPE.area VISIBLE;SHAPE.len SHAPE.len VISIBLE" SAME_AS_TEMPLATE SAME_AS_TEMPLATE # 0 "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisVector.GISADMIN.Towns" CopyFeatures Counties_poly_from_361_new S:\HQ\Planning\DataResources\Workspace\Mark\Assets.mdb\County_poly # 1000 0 0 AddField S:\HQ\Planning\DataResources\Workspace\Mark\Assets.mdb\County_poly F_AREA DOUBLE # # # # NULLABLE NON_REQUIRED # S:\HQ\Planning\DataResources\Workspace\Mark\Assets.mdb\County_poly CalculateAreas Counties_poly_from_361_new S:\HQ\Planning\DataResources\Workspace\Mark\Assets.mdb\County_poly FeatureClassToFeatureClass "Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Mark\gisdevelopment.GISPLANNER.Counties_poly" "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries" Counties2 # "COUNTY COUNTY true true false 20 Text 0 0 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Mark\gisdevelopment.GISPLANNER.Counties_poly,COUNTY,-1,-1;area area false false true 0 Double 0 0 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Mark\gisdevelopment.GISPLANNER.Counties_poly,Shape.area,-1,-1;len len false false true 0 Double 0 0 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Mark\gisdevelopment.GISPLANNER.Counties_poly,Shape.len,-1,-1" # "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties2" AddSpatialIndex "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties" 0 0 0 "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties" FeatureClassToFeatureClass "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties" "Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin" Counties2 # "COUNTY COUNTY true true false 20 Text 0 0 ,First,#,Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties,COUNTY,-1,-1;area area false true true 8 Double 8 38 ,First,#,Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties,gisvector.GISADMIN.Counties.area,-1,-1;len len false true true 8 Double 8 38 ,First,#,Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties,gisvector.GISADMIN.Counties.len,-1,-1;area_1 area_1 false false true 0 Double 0 0 ,First,#,Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties,Shape.area,-1,-1;len_1 len_1 false false true 0 Double 0 0 ,First,#,Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties,Shape.len,-1,-1" # "Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin\gisdevelopment.GISPLANNER.Counties2" FeatureClassToFeatureClass "Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin\gisdevelopment.GISPLANNER.Counties2" "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries" Counties # "COUNTY COUNTY true true false 20 Text 0 0 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin\gisdevelopment.GISPLANNER.Counties2,COUNTY,-1,-1;area area false true true 8 Double 8 38 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin\gisdevelopment.GISPLANNER.Counties2,gisdevelopment.GISPLANNER.Counties2.area,-1,-1;len len false true true 8 Double 8 38 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin\gisdevelopment.GISPLANNER.Counties2,gisdevelopment.GISPLANNER.Counties2.len,-1,-1;area_1 area_1 false true true 8 Double 8 38 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin\gisdevelopment.GISPLANNER.Counties2,area_1,-1,-1;len_1 len_1 false true true 8 Double 8 38 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin\gisdevelopment.GISPLANNER.Counties2,len_1,-1,-1;area_12 area_12 false false true 0 Double 0 0 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin\gisdevelopment.GISPLANNER.Counties2,Shape.area,-1,-1;len_12 len_12 false false true 0 Double 0 0 ,First,#,Database Connections\Planning Development.sde\gisDevelopment.GISPLANNER.Kevin\gisdevelopment.GISPLANNER.Counties2,Shape.len,-1,-1" # "Database Connections\Admin gisVector.sde\gisVector.GISADMIN.Boundaries\gisvector.GISADMIN.Counties" Project gisvector.GISADMIN.Counties "\\mhd-fsp-bos-v01\urd$\metcalfc\My Documents\ArcGIS\Default.gdb\Counties_Project1" GEOGCS['GCS_WGS_1984',DATUM['D_WGS_1984',SPHEROID['WGS_1984',6378137.0,298.257223563]],PRIMEM['Greenwich',0.0],UNIT['Degree',0.0174532925199433]] NAD_1983_To_WGS_1984_1 PROJCS['NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001',GEOGCS['GCS_North_American_1983',DATUM['D_North_American_1983',SPHEROID['GRS_1980',6378137.0,298.257222101]],PRIMEM['Greenwich',0.0],UNIT['Degree',0.0174532925199433]],PROJECTION['Lambert_Conformal_Conic'],PARAMETER['False_Easting',200000.0],PARAMETER['False_Northing',750000.0],PARAMETER['Central_Meridian',-71.5],PARAMETER['Standard_Parallel_1',41.71666666666667],PARAMETER['Standard_Parallel_2',42.68333333333333],PARAMETER['Latitude_Of_Origin',41.0],UNIT['Meter',1.0]] SimplifyPolygon Counties_Project1 \\mhd-fsp-bos-v01\urd$\metcalfc\Desktop\shapefilejs\counties.shp POINT_REMOVE "20 Meters" "0 SquareMeters" NO_CHECK NO_KEEP file://\\mhd-fsp-bos-v01\urd$\metcalfc\Desktop\shapefilejs\counties.shp Local Area Network counties 002 0.000 Geographic GCS_WGS_1984 Angular Unit: Degree (0.017453) <GeographicCoordinateSystem xsi:type='typens:GeographicCoordinateSystem' xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance' xmlns:xs='http://www.w3.org/2001/XMLSchema' xmlns:typens='http://www.esri.com/schemas/ArcGIS/10.0'><WKT>GEOGCS["GCS_WGS_1984",DATUM["D_WGS_1984",SPHEROID["WGS_1984",6378137.0,298.257223563]],PRIMEM["Greenwich",0.0],UNIT["Degree",0.0174532925199433],AUTHORITY["EPSG",4326]]</WKT><XOrigin>-399.99999999999989</XOrigin><YOrigin>-399.99999999999989</YOrigin><XYScale>11258999068426.24</XYScale><ZOrigin>-100000</ZOrigin><ZScale>10000</ZScale><MOrigin>-100000</MOrigin><MScale>10000</MScale><XYTolerance>8.9831528411952133e-009</XYTolerance><ZTolerance>0.001</ZTolerance><MTolerance>0.001</MTolerance><HighPrecision>true</HighPrecision><LeftLongitude>-180</LeftLongitude><WKID>4326</WKID></GeographicCoordinateSystem> 20130910 08492300 20130910 08492300 1.0 Server=mhd-gis-wh; Service=5151; Database=gisvector; User=gisadmin; Version=sde.DEFAULT REQUIRED: The name of an organization or individual that developed the data set. REQUIRED: The date when the data set is published or otherwise made available for release. gisvector.GISADMIN.Counties gisvector.GISADMIN.Counties vector digital data Microsoft Windows XP Version 5.1 (Build 2600) Service Pack 2; ESRI ArcCatalog 9.2.2.1350 en REQUIRED: A brief narrative summary of the data set. REQUIRED: A summary of the intentions with which the data set was developed. REQUIRED: The basis on which the time period of content information is determined. REQUIRED: The year (and optionally month, or month and day) for which the data set corresponds to the ground. REQUIRED: The state of the data set. REQUIRED: The frequency with which changes and additions are made to the data set after the initial data set is completed. REQUIRED: Western-most coordinate of the limit of coverage expressed in longitude. REQUIRED: Eastern-most coordinate of the limit of coverage expressed in longitude. REQUIRED: Northern-most coordinate of the limit of coverage expressed in latitude. REQUIRED: Southern-most coordinate of the limit of coverage expressed in latitude. REQUIRED: Reference to a formally registered thesaurus or a similar authoritative source of theme keywords. REQUIRED: Common-use word or phrase used to describe the subject of the data set. REQUIRED: Restrictions and legal prerequisites for accessing the data set. REQUIRED: Restrictions and legal prerequisites for using the data set after access is granted. SDE Feature Class Server=mhd-gis-wh; Service=5151; Database=gisvector; User=gisadmin; Version=sde.DEFAULT ArcSDE Connection 002 SDE Feature Class Shapefile 0.000 Dataset copied. Server=mhd-gis-wh; Service=esri_sde; Database=gisvector; User=gisviewer; Version=sde.DEFAULT 20061207 10363000 Dataset copied. 20061208 16173500 Dataset copied. \\MHD-Shared\SharedData$\HQ\Planning\DataResources\Workspace\Mark\Assets.mdb 20061211 10473400 Microsoft Windows 7 Version 6.1 (Build 7601) Service Pack 1; ESRI ArcGIS 10.0.5.4400 counties en FGDC Content Standards for Digital Geospatial Metadata FGDC-STD-001-1998 local time REQUIRED: The person responsible for the metadata information. REQUIRED: The organization responsible for the metadata information. REQUIRED: The mailing and/or physical address for the organization or individual. REQUIRED: The city of the address. REQUIRED: The state or province of the address. REQUIRED: The ZIP or other postal code of the address. REQUIRED: The telephone number by which individuals can speak to the organization or individual. 20070518 ISO 19115 Geographic Information - Metadata DIS_ESRI1.0 dataset Downloadable Data Vector Simple FALSE 0 FALSE FALSE GCS_North_American_1983 NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001 North American Datum of 1983 Geodetic Reference System 80 6378137.000000 298.257222 Explicit elevation coordinate included with horizontal coordinates 1.000000 NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001 EPSG 7.4.1 0 counties Feature Class 0 len_12 FID OID 4 0 0 Internal feature number. ESRI Sequential unique whole numbers that are automatically generated. Shape area_1 Double 19 0 0 Feature geometry. ESRI Coordinates defining the features. area_1 len_1 Double 19 0 0 area area Double 19 0 0 len len Double 19 0 0 len_1 COUNTY String 20 0 0 COUNTY Shape Geometry 0 0 0 Feature geometry. ESRI Coordinates defining the features. SHAPE area_12 Double 19 0 0 Feature geometry. ESRI Coordinates defining the features. area_12 len_12 Double 19 0 0 Shape_Leng Shape_Leng Double 19 0 0 Shape_Area Shape_Area Double 19 0 0 Area of feature in internal units squared. ESRI Positive real numbers that are automatically generated. 20130910
2 |
--------------------------------------------------------------------------------
/test/data/counties.shx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/counties.shx
--------------------------------------------------------------------------------
/test/data/counties.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/counties.zip
--------------------------------------------------------------------------------
/test/data/mixedcase.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/mixedcase.zip
--------------------------------------------------------------------------------
/test/data/noshp.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/noshp.zip
--------------------------------------------------------------------------------
/test/data/senate.dbf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/senate.dbf
--------------------------------------------------------------------------------
/test/data/senate.prj:
--------------------------------------------------------------------------------
1 | PROJCS["NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001",GEOGCS["GCS_North_American_1983",DATUM["D_North_American_1983",SPHEROID["GRS_1980",6378137.0,298.257222101]],PRIMEM["Greenwich",0.0],UNIT["Degree",0.0174532925199433]],PROJECTION["Lambert_Conformal_Conic"],PARAMETER["False_Easting",200000.0],PARAMETER["False_Northing",750000.0],PARAMETER["Central_Meridian",-71.5],PARAMETER["Standard_Parallel_1",41.71666666666667],PARAMETER["Standard_Parallel_2",42.68333333333333],PARAMETER["Latitude_Of_Origin",41.0],UNIT["Meter",1.0]]
--------------------------------------------------------------------------------
/test/data/senate.sbn:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/senate.sbn
--------------------------------------------------------------------------------
/test/data/senate.sbx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/senate.sbx
--------------------------------------------------------------------------------
/test/data/senate.shp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/senate.shp
--------------------------------------------------------------------------------
/test/data/senate.shp.xml:
--------------------------------------------------------------------------------
1 | 20120312 14003900 1.0 FGDC CSDGM Metadata FALSE 20130910 08390500 senate 002 33861.260000 330846.090100 777514.310000 959747.440000 1 file://\\mhd-fsp-bos-v01\urd$\metcalfc\Desktop\shapefilejs\senate.shp Local Area Network 0.000 Projected GCS_North_American_1983 NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001 <ProjectedCoordinateSystem xsi:type='typens:ProjectedCoordinateSystem' xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance' xmlns:xs='http://www.w3.org/2001/XMLSchema' xmlns:typens='http://www.esri.com/schemas/ArcGIS/10.0'><WKT>PROJCS["NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001",GEOGCS["GCS_North_American_1983",DATUM["D_North_American_1983",SPHEROID["GRS_1980",6378137.0,298.257222101]],PRIMEM["Greenwich",0.0],UNIT["Degree",0.0174532925199433]],PROJECTION["Lambert_Conformal_Conic"],PARAMETER["False_Easting",200000.0],PARAMETER["False_Northing",750000.0],PARAMETER["Central_Meridian",-71.5],PARAMETER["Standard_Parallel_1",41.71666666666667],PARAMETER["Standard_Parallel_2",42.68333333333333],PARAMETER["Latitude_Of_Origin",41.0],UNIT["Meter",1.0],AUTHORITY["EPSG",26986]]</WKT><XOrigin>-36530900</XOrigin><YOrigin>-28803200</YOrigin><XYScale>122610652.81195112</XYScale><ZOrigin>-100000</ZOrigin><ZScale>10000</ZScale><MOrigin>-100000</MOrigin><MScale>10000</MScale><XYTolerance>0.001</XYTolerance><ZTolerance>0.001</ZTolerance><MTolerance>0.001</MTolerance><HighPrecision>true</HighPrecision><WKID>26986</WKID></ProjectedCoordinateSystem> Linear Unit: Meter (1.000000) CopyFeatures "Database Connections\GISDATA_VT_DC.sde\GISDATA.SENATE2012_POLY" E:\MassGIS\mtrust\MassGIS_DataViewer_SHP\gisdata\men1\Political_Boundaries\SENATE2012_POLY.shp # 0 0 0 SimplifyPolygon SENATE2012_POLY \\mhd-fsp-bos-v01\urd$\metcalfc\Desktop\shapefilejs\senate.shp POINT_REMOVE "20 Meters" "0 SquareMeters" NO_CHECK NO_KEEP 20130910 08390500 FGDC /9j/4AAQSkZJRgABAQEAAQABAAD/2wBDAAgGBgcGBQgHBwcJCQgKDBQNDAsLDBkSEw8UHRofHh0a
2 | HBwgJC4nICIsIxwcKDcpLDAxNDQ0Hyc5PTgyPC4zNDL/2wBDAQkJCQwLDBgNDRgyIRwhMjIyMjIy
3 | MjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjL/wAARCACFAMgDASIA
4 | AhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQA
5 | AAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3
6 | ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWm
7 | p6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEA
8 | AwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSEx
9 | BhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElK
10 | U1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3
11 | uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD3+iii
12 | gAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKge6jCZjZJDnGA3A+p7VXF7uUyieDavBUOCo
13 | +rf5/Gsp14QdpMaTZfoqG1nFzbrMpBDZwVORwcVNWogooooAKKKKACiiigAooooAinkaNBsxvZgB
14 | kce/6A1F5lx/fi/74P8AjSyndcgdkX9T/wDq/WivMxOJnGpywexcYq2oefP/AM8Y/wDv4f8A4mmv
15 | dTIuTCnUDiQ9zj0p1MlQyRMoOCRwfQ9jWKxlXuPlRJ9pccNbuT/skEfqR/Kj7Uf+feX81/xqszTR
16 | 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 20130910 Microsoft Windows 7 Version 6.1 (Build 7601) Service Pack 1; ESRI ArcGIS 10.0.5.4400 State Senate Districts (2012) MassGIS One Ashburton Place, Room 1601 Boston MA 02108 USA 617-619-5611 Map of the Commonwealth of Massachusetts, Senate Districts, Chapter 152 of the Acts of 2011
74 | Bill: http://www.malegislature.gov/Bills/Detail?billNumber=s02045 002 -73.533350 -69.898477 42.888351 41.230341 1 Massachusetts General Court Special Joint Committee on Redistricting and MassGIS None MassGIS One Ashburton Place, Room 1601 Boston MA 02108 USA 617-619-5611 Senate 2012 Districts Senate 2012 Districts <DIV STYLE="text-align:Left;"><DIV><DIV><P><SPAN>Massachusetts Senate Districts (polygons) as signed into law on November 3, 2011. These districts were based on demographic data from the 2010 U.S. Census and are used for elections in 2012 and beyond until the districts are redrawn.</SPAN></P></DIV></DIV></DIV> Map of the Commonwealth of Massachusetts, Senate Districts, Chapter 152 of the Acts of 2011
75 | Bill: http://www.malegislature.gov/Bills/Detail?billNumber=s02045 Shapefile MassGIS One Ashburton Place, Room 1601 Boston MA 02108 USA 617-619-5611 Download from http://www.mass.gov/itd/senate2012 0.000 dataset EPSG 7.4.1 Vector Simple FALSE 0 FALSE FALSE 0 senate Feature Class 0 FID FID OID 4 0 0 Internal feature number. ESRI Sequential unique whole numbers that are automatically generated. SENDISTNUM SENDISTNUM Integer 5 5 0 Numeric Senate district identifier SEN_DIST SEN_DIST String 43 0 0 Name of Senate District SEN_FIRST SEN_FIRST String 13 0 0 Senator's first name SEN_LAST SEN_LAST String 15 0 0 Senator's last name SEN_PARTY SEN_PARTY String 3 0 0 Senator's political party SENATOR SENATOR String 40 0 0 Senator's full name and party URL URL String 150 0 0 Senator's Web site SHAPE Shape Geometry 0 0 0 Feature geometry. ESRI Coordinates defining the features. SHAPE_AREA SHAPE_AREA Double 19 0 0 Area of feature in internal units squared. ESRI Positive real numbers that are automatically generated. SHAPE_LEN SHAPE_LEN Double 19 0 0 State Senate Districts (2012) Massachusetts General Court Special Joint Committee on Redistricting and MassGIS 20130529 Massachusetts Senate Districts (polygons) as signed into law on November 3, 2011. These districts were based on demographic data from the 2010 U.S. Census and are used for elections in 2012 and beyond until the districts are redrawn. Senate 2012 Districts English Map of the Commonwealth of Massachusetts, Senate Districts, Chapter 152 of the Acts of 2011
76 | Bill: http://www.malegislature.gov/Bills/Detail?billNumber=s02045 None None Massachusetts General Court Special Joint Committee on Redistricting and MassGIS MassGIS mailing and physical address One Ashburton Place, Room 1601 Boston MA 02108 USA 617-619-5611 20130529 publication date Complete As needed None State Senate Districts (2012) None Commonwealth of Massachusetts SDE Feature Class 20130529 http://www.mass.gov/itd/senate2012 MassGIS Web Documentation MassGIS mailing and physical address One Ashburton Place, Room 1601 Boston MA 02108 USA 617-619-5611 MassGIS mailing and physical address One Ashburton Place, Room 1601 Boston MA 02108 USA 617-619-5611 Download from http://www.mass.gov/itd/senate2012 GCS_North_American_1983 NAD_1983_StatePlane_Massachusetts_Mainland_FIPS_2001 North American Datum of 1983 Geodetic Reference System 80 6378137.000000 298.257222 coordinate pair 0.010000 0.010000 meters Data obtained in early 2012 by MassGIS from the Massachusetts General Court Special Joint Committee on Redistricting. MassGIS added its 1:100,000 coastline and standardized attributes, followed by QA/QC procedures. Attribute updates on May 29 2013 ArcGIS 10.0 None None
77 |
--------------------------------------------------------------------------------
/test/data/senate.shx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/senate.shx
--------------------------------------------------------------------------------
/test/data/senate.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/senate.zip
--------------------------------------------------------------------------------
/test/data/train_stations.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/train_stations.zip
--------------------------------------------------------------------------------
/test/data/utf.cpg:
--------------------------------------------------------------------------------
1 | UTF-8
--------------------------------------------------------------------------------
/test/data/utf.dbf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/utf.dbf
--------------------------------------------------------------------------------
/test/data/utf.prj:
--------------------------------------------------------------------------------
1 | GEOGCS["GCS_WGS_1984",DATUM["D_WGS_1984",SPHEROID["WGS_1984",6378137,298.257223563]],PRIMEM["Greenwich",0],UNIT["Degree",0.017453292519943295]]
--------------------------------------------------------------------------------
/test/data/utf.qpj:
--------------------------------------------------------------------------------
1 | GEOGCS["WGS 84",DATUM["WGS_1984",SPHEROID["WGS 84",6378137,298.257223563,AUTHORITY["EPSG","7030"]],AUTHORITY["EPSG","6326"]],PRIMEM["Greenwich",0,AUTHORITY["EPSG","8901"]],UNIT["degree",0.0174532925199433,AUTHORITY["EPSG","9122"]],AUTHORITY["EPSG","4326"]]
2 |
--------------------------------------------------------------------------------
/test/data/utf.shp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/utf.shp
--------------------------------------------------------------------------------
/test/data/utf.shx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/utf.shx
--------------------------------------------------------------------------------
/test/data/utf.zip:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MikesWei/shapefile-js/7a6e63639e46e20f4bd23b0b71168fb96813cc2e/test/data/utf.zip
--------------------------------------------------------------------------------
/test/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Mocha Tests
5 |
6 |
7 |
8 |
9 |
10 |
15 |
16 |
17 |
18 |
21 |
22 |
23 |
--------------------------------------------------------------------------------
/test/test.js:
--------------------------------------------------------------------------------
1 | var shp = require('../');
2 | var chai = require('chai');
3 | chai.should();
4 | var chaiAsPromised = require("chai-as-promised");
5 |
6 | chai.use(chaiAsPromised);
7 |
8 | describe('Shp', function(){
9 | describe('park and rides not zipped', function(){
10 | var pandr = shp('http://localhost:3000/files/pandr');
11 | it('should have the right keys', function(){
12 | return pandr.should.eventually.contain.keys('type', 'features');
13 | });
14 | it('should be the right type',function(){
15 | return pandr.should.eventually.have.property('type', 'FeatureCollection');
16 | });
17 | it('should have the right number of features',function(){
18 | return pandr.then(function(a){return a.features;}).should.eventually.have.length(80);
19 | });
20 | });
21 | describe('park and rides zipped', function(){
22 | var pandr = shp('http://localhost:3000/files/pandr.zip');
23 | it('should have the right keys', function(){
24 | return pandr.should.eventually.contain.keys('type', 'features');
25 | });
26 | it('should be the right type',function(){
27 | return pandr.should.eventually.have.property('type', 'FeatureCollection');
28 | });
29 | it('should have the right number of features',function(){
30 | return pandr.then(function(a){return a.features}).should.eventually.have.length(80);
31 | });
32 | });
33 | describe('senate unzipped', function(){
34 | var pandr = shp('http://localhost:3000/test/data/senate');
35 | it('should have the right keys', function(){
36 | return pandr.should.eventually.contain.keys('type', 'features');
37 | });
38 | it('should be the right type',function(){
39 | return pandr.should.eventually.have.property('type', 'FeatureCollection');
40 | });
41 | it('should have the right number of features',function(){
42 | return pandr.then(function(a){return a.features}).should.eventually.have.length(40);
43 | });
44 | });
45 | describe('mixed case zipped', function(){
46 | var pandr = shp('http://localhost:3000/test/data/mixedcase.zip');
47 | it('should have the right keys', function(){
48 | return pandr.should.eventually.contain.keys('type', 'features');
49 | });
50 | it('should be the right type',function(){
51 | return pandr.should.eventually.have.property('type', 'FeatureCollection');
52 | });
53 | it('should have the right number of features',function(){
54 | return pandr.then(function(a){return a.features}).should.eventually.have.length(40);
55 | });
56 | });
57 | describe('senate zipped', function(){
58 | var pandr = shp('http://localhost:3000/test/data/senate.zip');
59 | it('should have the right keys', function(){
60 | return pandr.should.eventually.contain.keys('type', 'features');
61 | });
62 | it('should be the right type',function(){
63 | return pandr.should.eventually.have.property('type', 'FeatureCollection');
64 | });
65 | it('should have the right number of features',function(){
66 | return pandr.then(function(a){return a.features}).should.eventually.have.length(40);
67 | });
68 | });
69 | describe('county unzipped', function(){
70 | var pandr = shp('http://localhost:3000/test/data/counties');
71 | it('should have the right keys', function(){
72 | return pandr.should.eventually.contain.keys('type', 'features');
73 | });
74 | it('should be the right type',function(){
75 | return pandr.should.eventually.have.property('type', 'FeatureCollection');
76 | });
77 | it('should have the right number of features',function(){
78 | return pandr.then(function(a){return a.features}).should.eventually.have.length(14);
79 | });
80 | });
81 | describe('county zipped', function(){
82 | var pandr = shp('http://localhost:3000/test/data/counties.zip');
83 | it('should have the right keys', function(){
84 | return pandr.should.eventually.contain.keys('type', 'features');
85 | });
86 | it('should be the right type',function(){
87 | return pandr.should.eventually.have.property('type', 'FeatureCollection');
88 | });
89 | it('should have the right number of features',function(){
90 | return pandr.then(function(a){return a.features}).should.eventually.have.length(14);
91 | });
92 | });
93 | describe('trains zipped', function(){
94 | var pandr = shp('http://localhost:3000/test/data/train_stations.zip');
95 | it('should have the right keys', function(){
96 | return pandr.should.eventually.contain.keys('type', 'features');
97 | });
98 | it('should be the right type',function(){
99 | return pandr.should.eventually.have.property('type', 'FeatureCollection');
100 | });
101 | it('should have the right number of features',function(){
102 | return pandr.then(function(a){return a.features}).should.eventually.have.length(361);
103 | });
104 | });
105 | describe('empty attributes table', function(){
106 | var pandr = shp('http://localhost:3000/files/empty-shp.zip');
107 | it('should have the right keys', function(){
108 | return pandr.should.eventually.contain.keys('type', 'features');
109 | });
110 | it('should be the right type',function(){
111 | return pandr.should.eventually.have.property('type', 'FeatureCollection');
112 | });
113 | it('should have the right number of features',function(){
114 | return pandr.then(function(a){return a.features}).should.eventually.have.length(2);
115 | });
116 | });
117 | describe('errors', function(){
118 | it('bad file should be rejected', function(){
119 | return shp('http://localhost:3000/test/data/bad').should.be.rejected;
120 | });
121 | it('imaginary file file should be rejected', function(done){
122 | shp('http://localhost:3000/test/data/notthere').then(function () {
123 | done(true);
124 | }, function () {
125 | done();
126 | });
127 | });
128 | it('bad zip be rejected', function(){
129 | return shp('http://localhost:3000/test/data/badzip.zip').should.be.rejected;
130 | });
131 | it('no shp in zip', function(){
132 | return shp('http://localhost:3000/test/data/noshp.zip').should.be.rejected;
133 | });
134 | });
135 | describe('encoding', function () {
136 | it('should work for utf.zip', function(){
137 | return shp('http://localhost:3000/test/data/utf.zip').then(function (item) {
138 | item.should.contain.keys('type', 'features');
139 | return item.features.map(function (feature) {
140 | return feature.properties.field;
141 | });
142 | }).should.eventually.deep.equal([
143 | '💩',
144 | 'Hněvošický háj'
145 | ]);
146 | });
147 | it('should work for utf', function(){
148 | return shp('http://localhost:3000/test/data/utf').then(function (item) {
149 | item.should.contain.keys('type', 'features');
150 | return item.features.map(function (feature) {
151 | return feature.properties.field;
152 | });
153 | }).should.eventually.deep.equal([
154 | '💩',
155 | 'Hněvošický háj'
156 | ]);
157 | });
158 | it('should work for codepage.zip', function(){
159 | return shp('http://localhost:3000/test/data/codepage.zip').then(function (item) {
160 | item.should.contain.keys('type', 'features');
161 | return item.features.map(function (feature) {
162 | return feature.properties.field;
163 | });
164 | }).should.eventually.deep.equal([
165 | '??',
166 | 'Hněvošický háj'
167 | ]);
168 | });
169 | it('should work for codepage', function(){
170 | return shp('http://localhost:3000/test/data/codepage').then(function (item) {
171 | item.should.contain.keys('type', 'features');
172 | return item.features.map(function (feature) {
173 | return feature.properties.field;
174 | });
175 | }).should.eventually.deep.equal([
176 | '??',
177 | 'Hněvošický háj'
178 | ]);
179 | });
180 | });
181 | });
182 |
--------------------------------------------------------------------------------