Getting path length in mm SvgPathTools - python

I have an svg and I need to get the length of the paths in millimeters to be used in a real life application. Using the python svgpathtools library, using the length function works well but I cannot find anywhere in the docs for svpathtools what unit is used in calculating the length of the arc (or the curves included in it)
Below is the code I currently have
paths, attributes, svg_attributes = svg2paths2('sample.svg')
for path in paths:
for curve in path:
print(curve.length)
This is the output I receive from running the above code
10.895300154213514
15.142629055866722
23.730517433325748
23.73105785794831
21.77125455329005
11.279624921558746
11.279680843104023
21.771279269128605
23.731580549550927
23.731627915439564
21.77125455329005
11.279624921558746
11.279680843104023
21.774144213511132
23.729677579725156
23.731627915439564
21.795916354994993
10.986505331490429
10.604205974729867
46.43923310506517
45.3986468453268
10.324124024685046
8.071888088998016
0.003605551275512736
26.124050994562996
45.737106670828
53.94962464402549
17.012395710264993
51.95279012002064
16.17007686336362
20.841277156788127
78.72783591297403
17.23728179298918
55.8107820599928
48.672712650608986
0.0010000000000331966
27.058952638511517
68.02833313606227
18.822022537493844
45.413567277673636
45.42345206832466
19.62489493121194
44.61710566995185
22.870883374333967
29.565863874964815
34.33246812172493
45.73710667082802
37.11313707897945
2.842170943040401e-14

Related

Extruding an STL from a binary png image with python

I have been working on this code for a project at work which will (hopefully) take in images from a scanning electron microscope and generate 3D STL files of the structures were imaging. I'm at the stage with the code where I'm trying to generate a 3D structure from a 'coloured in' binary image I've made with some edge detection code I wrote. I came across this post How can i extrude a stl with python that basically does exactly what I need (generating a meshed 3D structure from a binary image). I've tried using/adapting the code in the answer to that post (see below) but I keep running into the following error: polyline2 = mr.distanceMapTo2DIsoPolyline(dm.value(), isoValue=127) RuntimeError: Bad expected access. I cant find anything online about why this is happening and I'm no expert in Python so have no idea myself. If anyone has an idea, I'd really appreciate it!
Code from answer to above post:
import meshlib.mrmeshpy as mr
# load image as Distance Map object:
dm = mr.loadDistanceMapFromImage(mr.Path("your-image.png"), 0)
# find boundary contour of the letter:
polyline2 = mr.distanceMapTo2DIsoPolyline(dm.value(), isoValue=127)
# triangulate the contour
mesh = mr.triangulateContours(polyline2.contours2())
# extrude itself:
mr.addBaseToPlanarMesh(mesh, zOffset=30)
# export the result:
mr.saveMesh(mesh, mr.Path("output-mesh.stl"))
I have tried the following:
Reconfigured the MeshLib package that this command uses. Package docs here: https://meshinspector.github.io/MeshLib/html/index.html#PythonIntegration
Updating VS studio/python/MeshLib
In older version of meshlib python module RuntimeError: Bad expected access indicated that mr.loadDistanceMapFromImage had failed, you should had checked it like this:
import meshlib.mrmeshpy as mr
# load image as Distance Map object:
dm = mr.loadDistanceMapFromImage(mr.Path("your-image.png"), 0)
# check dm
if ( not dm.has_value() ):
raise Exception(dm.error())
# find boundary contour of the letter:
polyline2 = mr.distanceMapTo2DIsoPolyline(dm.value(), isoValue=127)
# triangulate the contour
mesh = mr.triangulateContours(polyline2.contours2())
# extrude itself:
mr.addBaseToPlanarMesh(mesh, zOffset=30)
# export the result:
mr.saveMesh(mesh, mr.Path("output-mesh.stl"))
But in actual release your code will rise exception with real error.
Please make sure that path is correct, if it doesn't help please provide more info like png file and version of python and version of MeshLib and anything else you find related.
P.S. If there is real problem with MeshLib better open issue in github.

Python exifread - Parsing difficulties

I'm trying to get the coordinates of a number of photos, i.e. I'm trying to get the exif data using a python script. The goal is to georeference all the photos and display their locations on a map. I am encountering problems with exif, however. I'm on Windows (64bit) and installed the corresponding (Strawberry) Perl software and then the Exiftool module (version 12.30) using Anaconda (Navigator), but to no avail. It gives me the following error: ModuleNotFoundError: No module named 'exif'. If I use the command pip install exif it tells me that the requirements are already met. What am I missing here? I'll gladly provide more information if required.
... I also tried an alternative: the module exifread works without import problems but does not seem to have all the necessary functionality (I can read the coordinates, but can't handle the extraction of the coordinates, it gives me a IfdTag-object when I would like an array of the degrees, minutes and seconds that I can then further process.)
There is a utility function exifread.utils.get_gps_coord() that provides convenient method to access coordinates as tuple in the format (latitude, longitude). Note negative value for latitude means South, negative value for longitude - West
example
import exifread
path = 'image.jpg'
with open(path, 'rb') as f:
tags = exifread.process_file(f, details=False)
coord = exifread.utils.get_gps_coords(tags)
print(coord)
For sake of completeness, there are also other modules to work with exif:
Pillow - there is functionality to work with exif
piexif
Also, as mentioned in the comments - you can use ExifTool (Perl software), via subprocess

Increase graph size in plantUML from python?

MWE
To generate PlantUML diagrams in (sub)folder: /Diagrams/ I use the following python script:
from plantuml import PlantUML
import os
from os.path import abspath
from shutil import copyfile
os.environ['PLANTUML_LIMIT_SIZE'] = str(4096 * 4) # set max with to 4 times the default (16,384)
server = PlantUML(url='http://www.plantuml.com/plantuml/img/',
basic_auth={},
form_auth={}, http_opts={}, request_opts={})
diagram_dir = "./Diagrams"
#directory = os.fsencode()
for file in os.listdir(diagram_dir):
filename = os.fsdecode(file)
if filename.endswith(".txt"):
server.processes_file(abspath(f'./Diagrams/{filename}'))
It is used to generate for example the following test.txt file:
#startuml
'Enforce straight lines
skinparam linetype ortho
' Set direction of graph hierarchy
Left to Right direction
' create work package data
rectangle "something something something" as ffd0
rectangle "something something something" as ffd1
rectangle "something something something something something" as ffd2
rectangle "something something something something" as ffd3
rectangle "something something somethingsomethingsomething" as ffd4
rectangle "something something something something something something" as ffd5
rectangle "something something something something" as ffd6
rectangle "something something something " as ffd7
' Implement graph hierarchy
ffd0-->ffd1
ffd1-->ffd2
ffd2-->ffd3
ffd3-->ffd4
ffd4-->ffd5
ffd5-->ffd6
ffd6-->ffd7
#enduml
Expected behavior
Because I set the PLANTUML_LIMIT_SIZE variable to 16384 (pixels) as the FAQ suggests, I would expect this to fill up the picture of the diagram with all the blocks connected side by side up to a max width of 4096 * 4 pixels.
To test whether perhaps setting it from the python script was implemented incorrectly I also tried to set it manually with: set PLANTUML_LIMIT_SIZE=16384 to expect the same behavior as explained in the above paragraph (a picture filled up till 16384 pixels).
Observed behavior
Instead PlantUML cuts off the picture at 2000 horizontal pictures as shown in the figure below:
Question
How can I ensure the PlantUML does not cut off the blocks of the diagrams of n pixels (height or width), from a python script?
The best way I've found to prevent diagrams from being cut off, without trying to guess at the size or picking some arbitrarily large limit, is to select SVG output.
Note that setting PLANTUML_LIMIT_SIZE is only going to have an effect if you're running PlantUML locally, but it appears the Python interface you're using sends the diagram to the online service. I don't know the internals of that interface, but per the documentation you should be able to get SVG output by using http://www.plantuml.com/plantuml/svg/ as the service URL.
If you need the final image in PNG format, you will need to convert it with another tool.
Approach 1:
To prevent the diagram from being cut off I followed the following steps:
Downloaded the plantuml.jar from this location http://sourceforge.net/projects/plantuml/files/plantuml.jar/download
Put the diagram which I wrote in a someLargeDiagram.txt file, in the same directory as the plantuml.jar file.
Opened terminal on Ubuntu 20.04 in that same directory and ran:
java -jar plantuml.jar -verbose someLargeDiagram.txt
That successfully generated the diagram as .png file, which was not cut off.
Approach 2:
After creating even larger graphs, they got cut-off again, and it gave the message to increase the PLANTUML_LIMIT_SIZE. I tried passing the size as an argument in the commandline using: java -jar plantuml.jar -verbose -PLANTUML_LIMIT_SIZE=8192 Diagrams/latest.uml however that did not work, nor did ..-PLANTUML_LIMIT_SIZE 8192... This link suggested one could set it as an environment variable, so I did that in Ubuntu 20.04 using command: export PLANTUML_LIMIT_SIZE 8192, after which I successfully created a larger diagram that was not cut-off with command:
java -jar plantuml.jar -verbose Diagrams/latest.uml

Matching two vector paths

I have several vector paths and a query path and now I am trying to get the path which is most similar to the query path. I can access length(perimeter) of each path, and width and height of their bounding boxes. I am using python and using pyx library for rendering SVG paths and calculating their bounding boxes. Pseudo code looks like...
THRESHOLD = //some value
qpath = //my query path
similar_paths = []
for path in path_list:
if (comparable width and comparable height and comparable perimeters):
similar_paths.append(path)
But It does not seem to give nice results. Any ideas on how to improve the results?
Lets use a simple PyX graph to generate some paths:
The paths could also come from an SVG file read in parsed mode.
Once you have PyX paths, you can use PyX features to get further information about the paths. In the following simple version I calculate a few points along each path and the sum up their distance. (I do it using method names ending by _pt, which work in PostScript points. It is a little faster than using PyX units. Also I converted all paths to normpaths explicitely in the beginning. While this is not necessary, it helps reduces some function calls internally.)
Here is the full code (including the graph to generate the sample paths):
import math
from pyx import *
# create some data (and draw it)
g = graph.graphxy(width=10, x=graph.axis.lin(min=0, max=2*math.pi))
qpi = g.plot(graph.data.function("y(x)=sin(x)"))
opi1 = g.plot(graph.data.function("y(x)=sin(x)+0.1*sin(10*x)"))
opi2 = g.plot(graph.data.function("y(x)=sin(x)+0.2*sin(20*x)", points=1000))
g.writePDFfile()
# get the corresponding PyX paths
qpath = qpi.path.normpath()
opath1 = opi1.path.normpath()
opath2 = opi2.path.normpath()
# now analyse it
POINTS = 10
qpath_arclen_pt = qpath.arclen_pt()
qpath_points_pt = qpath.at_pt([qpath_arclen_pt*i/(POINTS-1) for i in range(POINTS)])
for opath in [opath1, opath2]:
opath_arclen_pt = opath.arclen_pt()
opath_points_pt = opath.at_pt([opath_arclen_pt*i/(POINTS-1) for i in range(POINTS)])
print(sum(math.sqrt((qpoint_x_pt-opoint_x_pt)**2 + (qpoint_y_pt-opoint_y_pt)**2)
for (qpoint_x_pt, qpoint_y_pt), (opoint_x_pt, opoint_y_pt) in zip(qpath_points_pt, opath_points_pt)))
The program just prints out:
25.381154890630064
56.44386644062556
which indicates, that the dashed lines is closer to the solid one than the dotted line.
You may also compare tangents, curvatures, the arclen itself etc. ... there are plenty of options depending on your needs.

R package Bio3D tutorial reproducing

I started working with R package called Bio3D
(http://thegrantlab.org/bio3d/index.php)
and encountered a problem during reproducing examples from "Protein Structure Networks with Bio3D" tutorial
(http://thegrantlab.org/bio3d/tutorials/protein-structure-networks).
Here is the fragment I am trying to do:
"
The code snippet below first sets the file paths for the example HIVpr starting structure (pdbfile) and trajectory data (dcdfile), then reads these files (producing the objects dcd and pdb).
dcdfile <- system.file("examples/hivp.dcd", package = "bio3d")
pdbfile <- system.file("examples/hivp.pdb", package = "bio3d")
# Read MD data
dcd <- read.dcd(dcdfile)
pdb <- read.pdb(pdbfile)
inds <- atom.select(pdb, resno = c(24:27, 85:90), elety = "CA")
trj <- fit.xyz(fixed = pdb$xyz, mobile = dcd,
fixed.inds = inds$xyz, mobile.inds = inds$xyz)
Once we have the superposed trajectory frames we can asses the extent to which the atomic fluctuations of individual residues (in this very short example simulation) are correlated with one another and build a network from this data:
cij <- dccm(trj)
net <- cna(cij)
plot(net, pdb)
"
And till this moment everything works well.
# View the correlations in pymol
view.dccm(cij, pdb, launch = FALSE)
Here I open generated pdb file corr.inpcrd with pymol.
But instead of nice cartoon 3D model I see just aminoacid residues represented by dots.
Tried to solve the problem with pymol using settings for cartoons, ribbons, colors, transparency and command show but it changed nothing.
Would be grateful for your suggestions!
I have not enough reputation to illustrate expected and obtained outcome with images but probably I will be able to send them directly if necessary.
Thank you!
Typically this will work if pymol is in your path for executables (see here: http://tinyurl.com/lzhpz3w for more about where bio3d expects to find pymol and muscle).
view.dccm(cij, pdb, launch = FALSE)
I don't use windows myself but if you post this question on the bio3d bitbucket issues page https://bitbucket.org/Grantlab/bio3d/issues you will get help from experienced windows bio3d users including the author of this function.
Try setting launch=TRUE in your call to the view.dccm() function to have both PDB and pymol script loaded for you.

Categories

Resources