Ich versuche, mit gnuplot 5.0 ein 2D-Datenarray ohne Ränder, Ränder oder Achsen zu zeichnen ... nur ein 2D-Bild (.png oder .jpg), das einige Daten darstellt. I haben möchte jedes Array - Element auf genau ein Pixel in dem Bild zu entsprechen , mit keiner Skalierung / Interpolation usw. und ohne zusätzliche weißen Pixel an den Rand.
Wenn ich bisher versuche, die Ränder auf 0 zu setzen und sogar das pixels
Flag zu verwenden, bleibt mir immer noch eine Reihe weißer Pixel am rechten und oberen Bildrand übrig.
Wie kann ich nur eine Bilddatei mit einer pixelweisen Darstellung eines Datenarrays und nichts extra erhalten?
Gnuplot-Skript:
#!/usr/bin/gnuplot --persist
set terminal png size 400, 200
set size ratio -1
set lmargin at screen 0
set rmargin at screen 1
set tmargin at screen 0
set bmargin at screen 1
unset colorbox
unset tics
unset xtics
unset ytics
unset border
unset key
set output "pic.png"
plot "T.dat" binary array=400x200 format="%f" with image pixels notitle
Beispieldaten aus Fortran 90:
program main
implicit none
integer, parameter :: nx = 400
integer, parameter :: ny = 200
real, dimension (:,:), allocatable :: T
allocate (T(nx,ny))
T(:,:)=0.500
T(2,2)=5.
T(nx-1,ny-1)=5.
T(2,ny-1)=5.
T(nx-1,2)=5.
open(3, file="T.dat", access="stream")
write(3) T(:,:)
close(3)
end program main
x y z
Listenformat vorliegen?Antworten:
Einige Gnuplot-Terminals implementieren "mit Bild", indem sie eine separate PNG-Datei erstellen, die das Bild enthält, und dann innerhalb des resultierenden Diagramms eine Verknüpfung dazu herstellen. Durch die direkte Verwendung dieser separaten PNG-Bilddatei werden Probleme mit dem Seitenlayout, den Rändern usw. vermieden. Hier verwende ich das Canvas-Terminal. Das Grundstück selbst wird weggeworfen; Alles, was wir behalten, ist die PNG-Datei, die mit dem gewünschten Inhalt erstellt wurde.
quelle
set term tikz externalimages
und dieses Terminal setzt den Zähler bei jedem "festgelegten Term" zurück. Sie können nichtset output "/dev/null"
mit tikz verwenden, aber wenn dies nicht funktioniert, um die Ausgabe für Sie zu unterdrücken, ist es Ihnen möglicherweise egal. Die Terminals tkcanvas und svg sind andere Möglichkeiten, aber der externe PNG-Mechanismus in diesen hängt von der Gnuplot-Version und den Kompilierungsoptionen ab.Verwenden Sie keinen Gnuplot.
Schreiben Sie stattdessen ein Skript, das Ihre Daten liest und in eines der Portable Anymap-Formate konvertiert . Hier ist ein Beispiel in Python:
Wenn Sie das Programm ändern können, das die Datendatei generiert, können Sie sogar den obigen Schritt überspringen und stattdessen die Daten direkt in einem PNM-Format generieren.
In beiden Fällen können Sie ImageMagick verwenden, um das Bild in ein Format Ihrer Wahl zu konvertieren:
quelle
imwrite
Funktion können 2D-Daten als PNG-Bild gespeichert werden.gnuplot
ich siematplotlib
stattdessen (siehe meine Antwort unten). Dies ist ein großartiger Beitrag, aber technisch gesehen verlangt die Frage / Prämie nach einergnuplot
Lösung, so ungeeignet sie für diese spezielle Aufgabe zu sein scheint.Dies sollte eine leichte Aufgabe sein, ist es aber anscheinend nicht. Das Folgende könnte eine (umständliche) Lösung sein, da alle anderen Versuche fehlgeschlagen sind. Mein Verdacht ist, dass einige Grafikbibliotheken ein Problem haben, das Sie als Gnuplot-Benutzer wahrscheinlich nicht lösen können.
Sie haben erwähnt, dass ASCII-Matrixdaten ebenfalls in Ordnung sind. Der "Trick" besteht darin, Daten zu zeichnen, bei
with lines
denen die Daten durch leere Linien "unterbrochen" werden, wobei im Grunde einzelne Punkte gezeichnet werden. Überprüfen Sie dies, falls Sie Ihre Datendatei 1: 1 in einen Datenblock übertragen müssen .Wenn es jedoch nicht schon seltsam genug ist, scheint es für
png
undgif
terminal zu funktionieren, aber nicht fürpngcairo
oderwxt
. Ich denke, die Problemumgehung ist wahrscheinlich langsam und ineffizient, aber zumindest wird die gewünschte Ausgabe erstellt. Ich bin mir nicht sicher, ob es eine Größenbeschränkung gibt. Getestet mit 100x100 Pixel mit Win7, Gnuplot 5.2.6. Kommentare und Verbesserungen sind willkommen.Code:
Ergebnis: (100x100 Pixel)
(vergrößert mit schwarzem Hintergrund):
Bild mit 400 x 200 Pixel (dauert auf meinem 8 Jahre alten Laptop ungefähr 22 Sekunden).
quelle
x
undy
. Es funktioniert immer noch, wennSizeX
undSizeY
nicht gleich. Ich werde den Code korrigieren.Data2
?Was ich letztendlich tatsächlich verwendet habe, um das zu bekommen, was ich brauchte , obwohl die Frage / das Kopfgeld nach einer
gnuplot
Lösung fragt :matplotlib
hat eine Funktion matplotlib.pyplot.imsave, die genau das tut, wonach ich gesucht habe ... dh "nur Datenpixel " und keine Extras wie Ränder, Ränder, Achsen usw. zeichnen . Ursprünglich wusste ich nur über matplotlib.pyplot.imshow Bescheid und musste Ziehen Sie viele Tricks, um alle Extras aus der Bilddatei zu entfernen und Interpolation / Glättung usw. zu verhindern (und wenden Sie sich dahergnuplot
an einen bestimmten Punkt). Daimsave
es ziemlich einfach ist, verwende ich wiedermatplotlib
eine einfache und dennoch flexible Lösung (in Bezug auf Farbkarte, Skalierung usw.) für "pixelgenaue" Diagramme. Hier ist ein Beispiel:quelle
OK, hier ist eine andere mögliche Lösung (ich habe sie von meinem ersten umständlichen Ansatz getrennt). Es erstellt die Handlung sofort, weniger als eine Sekunde. Kein Umbenennen oder Erstellen einer nutzlosen Datei erforderlich.
Ich denke, Schlüssel ist zu verwenden
term png
undps 0.1
.Ich habe keinen Beweis, aber ich denke,
ps 1
wäre ca. 6 Pixel groß und würde einige Überlappungen und / oder weiße Pixel an der Ecke erzeugen. Wiederum, aus welchem Grund auch immer, scheint es zu funktionieren,term png
aber nicht mitterm pngcairo
.Was ich getestet habe (Win7, Gnuplot 5.2.6), ist eine Binärdatei mit dem Muster
00 00 FF
überall wiederholt wird (ich kann hier keine Null-Bytes anzeigen). Da Gnuplot anscheinend 4 Bytes pro Array-Element (format="%d"
) liest , führt dies zu einem alternierenden RGB-Muster, wenn ich plottewith lc rgb var
.Auf die gleiche Weise (hoffentlich) können wir herausfinden, wie man liest
format="%f"
und zusammen mit einer Farbpalette verwendet. Ich denke, das ist es, wonach du suchst, oder? Weitere Testergebnisse, Kommentare, Verbesserungen und Erklärungen sind willkommen.Code:
Ergebnis:
quelle