Comments (2)
Thanks for raising this issue. My apologies for not replier sooner. I'm not sure why I havent seen this issue before.
Your problem is interesting and I have no idea if topojson
can be of value here. I tried a few things, but I didn't get as close as your result, so probably you got already further than I did.
Anyway what I tried is using the prequantize
and presimplify
options, while setting topology
to False, since you are merely aiming for a combination of simplification and quantization, I think.
This is what I tried
import cv2
import numpy as np
from collections import defaultdict
from shapely.geometry import MultiPolygon, Polygon
from matplotlib import pyplot as plt
import topojson as tp
# function from here: https://michhar.github.io/masks_to_polygons_and_back/
def mask_to_polygons(mask, min_area=10.):
"""Convert a mask ndarray (binarized image) to Multipolygons"""
# first, find contours with cv2: it's much faster than shapely
contours, hierarchy = cv2.findContours(mask,
cv2.RETR_CCOMP,
cv2.CHAIN_APPROX_NONE)
if not contours:
return MultiPolygon()
# now messy stuff to associate parent and child contours
cnt_children = defaultdict(list)
child_contours = set()
assert hierarchy.shape[0] == 1
# http://docs.opencv.org/3.1.0/d9/d8b/tutorial_py_contours_hierarchy.html
for idx, (_, _, _, parent_idx) in enumerate(hierarchy[0]):
if parent_idx != -1:
child_contours.add(idx)
cnt_children[parent_idx].append(contours[idx])
# create actual polygons filtering by area (removes artifacts)
all_polygons = []
for idx, cnt in enumerate(contours):
if idx not in child_contours and cv2.contourArea(cnt) >= min_area:
assert cnt.shape[1] == 1
poly = Polygon(
shell=cnt[:, 0, :],
holes=[c[:, 0, :] for c in cnt_children.get(idx, [])
if cv2.contourArea(c) >= min_area])
all_polygons.append(poly)
all_polygons = MultiPolygon(all_polygons)
return all_polygons
img = cv2.imread(r'/Users/mattijnvanhoek/Downloads/110661906-f8751b80-81ff-11eb-87e3-91b1d545c015.png', cv2.IMREAD_UNCHANGED)
plt.imshow(img)
edges = cv2.Canny(img, 1, 1)
plt.imshow(edges, cmap='gray', interpolation='bicubic')
poly = mask_to_polygons(edges, min_area=1)
poly # seems to be reversed, but not important now
# low prequantize values only work with the topojson version 1.1
# !python -m pip install git+https://github.com/mattijn/topojson.git --upgrade
tp.Topology(poly, prequantize=False, presimplify=200, topology=False).to_alt()
tp.Topology(poly, prequantize=50, presimplify=False, topology=False).to_alt()
from topojson.
Hi Matt, sorry for my late reply. I have tried different options and couldn't "merge" the neighbouring points (from difference polygons) together. So I just loop through all the points and manually merged the points together.
My use case is convert a bitmap mask (from semantic segmentation result from a deep learning model) to vectorized results. Maybe it's a good feature for you to add. Let me know if here is anything I can contribute.
from topojson.
Related Issues (20)
- Merge multiple layers in a single topojson HOT 5
- Conversion to Typology object causes overlaps HOT 5
- tp.Topology.to_json(pretty=True) doesn't handle None correctly. (Doens't convert None to null) HOT 1
- Converting GeoJSON FeatureCollection to TopoJSON HOT 1
- BUG: `Topology.to_gdf` should keep the original index HOT 2
- holes in multipolygons are lost by simplification HOT 4
- Deprecation warning for shapely 2.0 HOT 3
- Wrong topologies/arcs being created? HOT 7
- Creating a topology for data without junctions and shared_coords=False, prequantize=False gives error
- Bug: polygons that entirely fill islands in another polygon are often not dedupped
- shared_coords=True vs shared_coords=False HOT 5
- Linestrings that follow the same path but where one contains extra redundant points are not deduplicated
- enh: include features that are possible with shapely 2.0
- tests failing, natural earth dataset changed HOT 2
- RuntimeWarning: invalid value encountered in cast HOT 3
- IndexError: pop index out of range when instanciating Topology with a list of GeoDataFrame HOT 10
- Coordinates not reported correctly on Multipoint with only one point HOT 2
- Excessive memory usage with prequantization enabled HOT 5
- serialize_as_geojson outputs invalid GeoJSON HOT 2
- Topojson >=1.6 requires Python >=3.8, but there is no guard against Python <3.8 HOT 2
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from topojson.