33 Feature ,
44 Geometry ,
55 LineString ,
6+ MultiLineString ,
67 MultiPoint ,
78 MultiPolygon ,
89 Point ,
@@ -87,8 +88,18 @@ function booleanContains(
8788 }
8889 case "MultiPolygon" :
8990 switch ( type2 ) {
91+ case "Point" :
92+ return isPointInMultiPolygon ( geom1 , geom2 ) ;
93+ case "MultiPoint" :
94+ return isMultiPointInMultiPolygon ( geom1 , geom2 ) ;
95+ case "LineString" :
96+ return isLineInMultiPolygon ( geom1 , geom2 ) ;
97+ case "MultiLineString" :
98+ return isMultiLineStringInMultiPolygon ( geom1 , geom2 ) ;
9099 case "Polygon" :
91100 return isPolygonInMultiPolygon ( geom1 , geom2 ) ;
101+ case "MultiPolygon" :
102+ return isMultiPolygonInMultiPolygon ( geom1 , geom2 ) ;
92103 default :
93104 throw new Error ( "feature2 " + type2 + " geometry not supported" ) ;
94105 }
@@ -103,6 +114,122 @@ function isPolygonInMultiPolygon(multiPolygon: MultiPolygon, polygon: Polygon) {
103114 ) ;
104115}
105116
117+ /**
118+ * Is Point inside MultiPolygon
119+ *
120+ * @private
121+ * @param {MultiPolygon } multiPolygon MultiPolygon geometry
122+ * @param {Point } point Point geometry
123+ * @returns {boolean } true if point is inside the interior of any polygon in the MultiPolygon
124+ */
125+ function isPointInMultiPolygon ( multiPolygon : MultiPolygon , point : Point ) {
126+ return multiPolygon . coordinates . some ( ( coords ) =>
127+ booleanPointInPolygon (
128+ point ,
129+ { type : "Polygon" , coordinates : coords } ,
130+ {
131+ ignoreBoundary : true ,
132+ }
133+ )
134+ ) ;
135+ }
136+
137+ /**
138+ * Is MultiPoint inside MultiPolygon
139+ *
140+ * @private
141+ * @param {MultiPolygon } multiPolygon MultiPolygon geometry
142+ * @param {MultiPoint } multiPoint MultiPoint geometry
143+ * @returns {boolean } true if every point is inside the interior of some polygon in the MultiPolygon
144+ */
145+ function isMultiPointInMultiPolygon (
146+ multiPolygon : MultiPolygon ,
147+ multiPoint : MultiPoint
148+ ) {
149+ for ( const coord of multiPoint . coordinates ) {
150+ const pointInside = multiPolygon . coordinates . some ( ( polyCoords ) =>
151+ booleanPointInPolygon (
152+ coord ,
153+ { type : "Polygon" , coordinates : polyCoords } ,
154+ { ignoreBoundary : true }
155+ )
156+ ) ;
157+ if ( ! pointInside ) {
158+ return false ;
159+ }
160+ }
161+ return true ;
162+ }
163+
164+ /**
165+ * Is LineString inside MultiPolygon
166+ *
167+ * @private
168+ * @param {MultiPolygon } multiPolygon MultiPolygon geometry
169+ * @param {LineString } lineString LineString geometry
170+ * @returns {boolean } true if the LineString is fully contained within a single polygon of the MultiPolygon
171+ */
172+ function isLineInMultiPolygon (
173+ multiPolygon : MultiPolygon ,
174+ lineString : LineString
175+ ) {
176+ return multiPolygon . coordinates . some ( ( coords ) =>
177+ isLineInPoly ( { type : "Polygon" , coordinates : coords } , lineString )
178+ ) ;
179+ }
180+
181+ /**
182+ * Is MultiLineString inside MultiPolygon
183+ *
184+ * @private
185+ * @param {MultiPolygon } multiPolygon MultiPolygon geometry
186+ * @param {MultiLineString } multiLineString MultiLineString geometry
187+ * @returns {boolean } true if every LineString is fully contained within some single polygon of the MultiPolygon
188+ */
189+ function isMultiLineStringInMultiPolygon (
190+ multiPolygon : MultiPolygon ,
191+ multiLineString : MultiLineString
192+ ) {
193+ for ( const lineCoords of multiLineString . coordinates ) {
194+ const lineInside = multiPolygon . coordinates . some ( ( polyCoords ) =>
195+ isLineInPoly (
196+ { type : "Polygon" , coordinates : polyCoords } ,
197+ { type : "LineString" , coordinates : lineCoords }
198+ )
199+ ) ;
200+ if ( ! lineInside ) {
201+ return false ;
202+ }
203+ }
204+ return true ;
205+ }
206+
207+ /**
208+ * Is MultiPolygon inside MultiPolygon
209+ *
210+ * @private
211+ * @param {MultiPolygon } multiPolygon1 MultiPolygon geometry (container)
212+ * @param {MultiPolygon } multiPolygon2 MultiPolygon geometry (contained)
213+ * @returns {boolean } true if every polygon of multiPolygon2 is fully contained within some single polygon of multiPolygon1
214+ */
215+ function isMultiPolygonInMultiPolygon (
216+ multiPolygon1 : MultiPolygon ,
217+ multiPolygon2 : MultiPolygon
218+ ) {
219+ for ( const poly2Coords of multiPolygon2 . coordinates ) {
220+ const polyInside = multiPolygon1 . coordinates . some ( ( poly1Coords ) =>
221+ isPolyInPoly (
222+ { type : "Polygon" , coordinates : poly1Coords } ,
223+ { type : "Polygon" , coordinates : poly2Coords }
224+ )
225+ ) ;
226+ if ( ! polyInside ) {
227+ return false ;
228+ }
229+ }
230+ return true ;
231+ }
232+
106233function isMultiPolyInPoly ( polygon : Polygon , multiPolygon : MultiPolygon ) {
107234 return multiPolygon . coordinates . every ( ( coords ) =>
108235 isPolyInPoly ( polygon , { type : "Polygon" , coordinates : coords } )
0 commit comments