mirror of
https://github.com/meteoinfo/MeteoInfo.git
synced 2025-12-08 20:36:05 +00:00
add contour3 plot function
This commit is contained in:
parent
37fb27ed17
commit
40d21f0e76
@ -3673,6 +3673,81 @@ public class GraphicFactory {
|
||||
return graphics;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create 3-D contour lines
|
||||
*
|
||||
* @param xa X coordinate array - one dimension
|
||||
* @param ya Y coordinate array - one dimension
|
||||
* @param za Z coordinate array - two dimension
|
||||
* @param ls Legend scheme
|
||||
* @param isSmooth Is smooth or not
|
||||
* @return Contour lines
|
||||
*/
|
||||
public static GraphicCollection createContourLines3D(Array xa, Array ya, Array za, LegendScheme ls, boolean isSmooth) {
|
||||
xa = xa.copyIfView();
|
||||
ya = ya.copyIfView();
|
||||
za = za.copyIfView();
|
||||
|
||||
ls = ls.convertTo(ShapeTypes.POLYLINE);
|
||||
Object[] ccs = LegendManage.getContoursAndColors(ls);
|
||||
double[] cValues = (double[]) ccs[0];
|
||||
|
||||
int[] shape = za.getShape();
|
||||
int[][] S1 = new int[shape[0]][shape[1]];
|
||||
double[] x = (double[])ArrayUtil.copyToNDJavaArray_Double(xa);
|
||||
double[] y = (double[])ArrayUtil.copyToNDJavaArray_Double(ya);
|
||||
if (x[1] - x[0] < 0) {
|
||||
ArrayUtils.reverse(x);
|
||||
za = za.flip(1);
|
||||
}
|
||||
if (y[1] - y[0] < 0) {
|
||||
ArrayUtils.reverse(y);
|
||||
za = za.flip(0);
|
||||
}
|
||||
double missingValue = -9999.0;
|
||||
double[][] data = (double[][]) ArrayUtil.copyToNDJavaArray_Double(za, missingValue);
|
||||
Object[] cbs = ContourDraw.tracingContourLines(data,
|
||||
cValues, x, y, missingValue, S1);
|
||||
List<PolyLine> ContourLines = (List<PolyLine>) cbs[0];
|
||||
|
||||
if (ContourLines.isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
if (isSmooth) {
|
||||
ContourLines = Contour.smoothLines(ContourLines);
|
||||
}
|
||||
|
||||
PolyLine aLine;
|
||||
double v;
|
||||
ColorBreak cbb;
|
||||
GraphicCollection3D graphics = new GraphicCollection3D();
|
||||
BivariateFunction interpolator = InterpUtil.getBiInterpFunc(xa, ya, za.transpose(0, 1), "linear");
|
||||
for (int i = 0; i < ContourLines.size(); i++) {
|
||||
aLine = ContourLines.get(i);
|
||||
v = aLine.Value;
|
||||
|
||||
PolylineZShape aPolyline = new PolylineZShape();
|
||||
PointZ aPoint;
|
||||
List<PointZ> pList = new ArrayList<>();
|
||||
for (int j = 0; j < aLine.PointList.size(); j++) {
|
||||
aPoint = new PointZ();
|
||||
aPoint.X = aLine.PointList.get(j).X;
|
||||
aPoint.Y = aLine.PointList.get(j).Y;
|
||||
aPoint.Z = interpolator.value(aPoint.X, aPoint.Y);
|
||||
pList.add(aPoint);
|
||||
}
|
||||
aPolyline.setPoints(pList);
|
||||
aPolyline.setValue(v);
|
||||
cbb = ls.findLegendBreak(v);
|
||||
graphics.add(new Graphic(aPolyline, cbb));
|
||||
}
|
||||
graphics.setSingleLegend(false);
|
||||
graphics.setLegendScheme(ls);
|
||||
|
||||
return graphics;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create contour lines
|
||||
*
|
||||
|
||||
@ -1,36 +1,36 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<MeteoInfo File="milconfig.xml" Type="configurefile">
|
||||
<Path OpenPath="D:\Working\MIScript\Jython\mis\dataframe">
|
||||
<Path OpenPath="D:\Working\MIScript\Jython\mis\plot_types\3d\jogl\contour">
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\io"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\io\burf"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\LaSW"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\LaSW\ZhengZhou"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\contour"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\3d\jogl\slice"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\3d\jogl\contour"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\funny"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\array"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\3d"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\3d\jogl"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\3d\jogl\surf"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\dataframe"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\3d\jogl"/>
|
||||
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\3d\jogl\contour"/>
|
||||
</Path>
|
||||
<File>
|
||||
<OpenedFiles>
|
||||
<OpenedFile File="D:\MyProgram\java\MeteoInfoDev\toolbox\meteoview3d\_reload.py"/>
|
||||
<OpenedFile File="D:\MyProgram\java\MeteoInfoDev\toolbox\meteoview3d\mainGUI.py"/>
|
||||
<OpenedFile File="D:\Working\MIScript\Jython\mis\dataframe\loc_2.py"/>
|
||||
<OpenedFile File="D:\Working\MIScript\Jython\mis\dataframe\replace_3.py"/>
|
||||
<OpenedFile File="D:\Working\MIScript\Jython\mis\dataframe\loc_1.py"/>
|
||||
<OpenedFile File="D:\Working\MIScript\Jython\mis\dataframe\replace_4.py"/>
|
||||
</OpenedFiles>
|
||||
<RecentFiles>
|
||||
<RecentFile File="D:\MyProgram\java\MeteoInfoDev\toolbox\meteoview3d\_reload.py"/>
|
||||
<RecentFile File="D:\MyProgram\java\MeteoInfoDev\toolbox\meteoview3d\mainGUI.py"/>
|
||||
<RecentFile File="D:\Working\MIScript\Jython\mis\dataframe\loc_2.py"/>
|
||||
<RecentFile File="D:\Working\MIScript\Jython\mis\dataframe\replace_3.py"/>
|
||||
<RecentFile File="D:\Working\MIScript\Jython\mis\dataframe\loc_1.py"/>
|
||||
<RecentFile File="D:\Working\MIScript\Jython\mis\dataframe\replace_4.py"/>
|
||||
</RecentFiles>
|
||||
</File>
|
||||
<Font>
|
||||
|
||||
Binary file not shown.
@ -1265,6 +1265,74 @@ class Axes3D(Axes):
|
||||
if visible:
|
||||
self.add_graphic(igraphic)
|
||||
return igraphic
|
||||
|
||||
def contour3(self, *args, **kwargs):
|
||||
"""
|
||||
3-D contour plot.
|
||||
|
||||
:param x: (*array_like*) Optional. X coordinate array.
|
||||
:param y: (*array_like*) Optional. Y coordinate array.
|
||||
:param z: (*array_like*) 2-D z value array.
|
||||
:param levels: (*array_like*) Optional. A list of floating point numbers indicating the level curves
|
||||
to draw, in increasing order.
|
||||
:param cmap: (*string*) Color map string.
|
||||
:param colors: (*list*) If None (default), the colormap specified by cmap will be used. If a
|
||||
string, like ‘r’ or ‘red’, all levels will be plotted in this color. If a tuple of matplotlib
|
||||
color args (string, float, rgb, etc), different levels will be plotted in different colors in
|
||||
the order specified.
|
||||
:param smooth: (*boolean*) Smooth contour lines or not.
|
||||
|
||||
:returns: (*graphics*) Contour graphics created from array data.
|
||||
"""
|
||||
n = len(args)
|
||||
cmap = plotutil.getcolormap(**kwargs)
|
||||
fill_value = kwargs.pop('fill_value', -9999.0)
|
||||
offset = kwargs.pop('offset', 0)
|
||||
if n <= 2:
|
||||
z = args[0]
|
||||
if isinstance(z, DimArray):
|
||||
y = z.dimvalue(0)
|
||||
x = z.dimvalue(1)
|
||||
else:
|
||||
x = np.arange(z.shape[1])
|
||||
y = np.arange(z.shape[0])
|
||||
args = args[1:]
|
||||
else:
|
||||
x = args[0]
|
||||
y = args[1]
|
||||
z = args[2]
|
||||
args = args[3:]
|
||||
|
||||
if x.ndim == 2:
|
||||
x = x[0]
|
||||
if y.ndim == 2:
|
||||
y = y[:,0]
|
||||
|
||||
if len(args) > 0:
|
||||
level_arg = args[0]
|
||||
if isinstance(level_arg, int):
|
||||
cn = level_arg
|
||||
ls = LegendManage.createLegendScheme(z.min(), z.max(), cn, cmap)
|
||||
else:
|
||||
if isinstance(level_arg, NDArray):
|
||||
level_arg = level_arg.aslist()
|
||||
ls = LegendManage.createLegendScheme(z.min(), z.max(), level_arg, cmap)
|
||||
else:
|
||||
ls = LegendManage.createLegendScheme(z.min(), z.max(), cmap)
|
||||
ls = ls.convertTo(ShapeTypes.POLYLINE)
|
||||
plotutil.setlegendscheme(ls, **kwargs)
|
||||
|
||||
smooth = kwargs.pop('smooth', True)
|
||||
igraphic = GraphicFactory.createContourLines3D(x.asarray(), y.asarray(), z.asarray(), ls, smooth)
|
||||
|
||||
lighting = kwargs.pop('lighting', None)
|
||||
if not lighting is None:
|
||||
igraphic.setUsingLight(lighting)
|
||||
|
||||
visible = kwargs.pop('visible', True)
|
||||
if visible:
|
||||
self.add_graphic(igraphic)
|
||||
return igraphic
|
||||
|
||||
def contourf(self, *args, **kwargs):
|
||||
"""
|
||||
|
||||
Binary file not shown.
@ -41,7 +41,7 @@ g_axes = None
|
||||
__all__ = [
|
||||
'annotate', 'antialias', 'arrow', 'arrowline', 'axes', 'axes3d', 'axes3dgl', 'axesm', 'caxes', 'axis',
|
||||
'axism', 'bar', 'bar3', 'barh', 'barbs', 'barbsm', 'bgcolor', 'box', 'boxplot', 'windrose', 'cla',
|
||||
'clabel', 'clc', 'clear', 'clf', 'cll', 'cloudspec', 'colorbar', 'contour', 'contourf',
|
||||
'clabel', 'clc', 'clear', 'clf', 'cll', 'cloudspec', 'colorbar', 'contour', 'contour3', 'contourf',
|
||||
'contourfm', 'contourm', 'contourfslice', 'contourslice', 'delfig', 'draw', 'draw_if_interactive',
|
||||
'errorbar', 'figure', 'glfigure', 'figsize', 'patch', 'rectangle', 'fill', 'fill3', 'fill_between',
|
||||
'fill_betweenx', 'fimplicit3', 'webmap', 'gca', 'gcf', 'gc_collect', 'geoshow', 'get_figure',
|
||||
@ -2079,6 +2079,20 @@ def slice3(*args, **kwargs):
|
||||
return r
|
||||
|
||||
|
||||
@_copy_docstring_and_deprecators(Axes3D.contour3)
|
||||
def contour3(*args, **kwargs):
|
||||
global g_axes
|
||||
if g_axes is None:
|
||||
g_axes = axes3d()
|
||||
else:
|
||||
if not isinstance(g_axes, Axes3DGL):
|
||||
g_axes = axes3dgl()
|
||||
|
||||
r = g_axes.contour3(*args, **kwargs)
|
||||
draw_if_interactive()
|
||||
return r
|
||||
|
||||
|
||||
@_copy_docstring_and_deprecators(Axes3DGL.contourslice)
|
||||
def contourslice(*args, **kwargs):
|
||||
global g_axes
|
||||
|
||||
@ -224,6 +224,30 @@ public enum DataType {
|
||||
return (this == DataType.ENUM1) || (this == DataType.ENUM2) || (this == DataType.ENUM4);
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert a number to this data type
|
||||
* @param n The number
|
||||
* @return New data type number
|
||||
*/
|
||||
public Number asNumber(Number n) {
|
||||
switch (this) {
|
||||
case INT:
|
||||
return n.intValue();
|
||||
case BYTE:
|
||||
return n.byteValue();
|
||||
case FLOAT:
|
||||
return n.floatValue();
|
||||
case DOUBLE:
|
||||
return n.doubleValue();
|
||||
case SHORT:
|
||||
return n.shortValue();
|
||||
case LONG:
|
||||
return n.longValue();
|
||||
default:
|
||||
return n;
|
||||
}
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////
|
||||
/**
|
||||
* Find the DataType that matches this name.
|
||||
@ -379,7 +403,6 @@ public enum DataType {
|
||||
static public short unsignedByteToShort(byte b) {
|
||||
return (short) (b & 0xff);
|
||||
}
|
||||
// return (short)((b<0)? (short)b + 256 : (short)b);
|
||||
|
||||
public static void main(String[] args) {
|
||||
for (int i = 0; i < 260; i++) {
|
||||
|
||||
@ -8597,6 +8597,9 @@ public class ArrayMath {
|
||||
* @param value New value
|
||||
*/
|
||||
public static void replaceValue(Array a, Object oValue, Object value) {
|
||||
if (oValue instanceof Number) {
|
||||
oValue = a.getDataType().asNumber((Number) oValue);
|
||||
}
|
||||
if (a.getIndexPrivate().isFastIterator()) {
|
||||
for (int i = 0; i < a.getSize(); i++) {
|
||||
if (oValue.equals(a.getObject(i))) {
|
||||
@ -8652,6 +8655,31 @@ public class ArrayMath {
|
||||
return n;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert a number to data type
|
||||
* @param v Number value
|
||||
* @param dt Data type
|
||||
* @return Number
|
||||
*/
|
||||
public static Number toDataType(Number v, DataType dt) {
|
||||
switch (dt) {
|
||||
case INT:
|
||||
case BOOLEAN:
|
||||
return v.intValue();
|
||||
case FLOAT:
|
||||
return v.floatValue();
|
||||
case SHORT:
|
||||
return v.shortValue();
|
||||
case BYTE:
|
||||
return v.byteValue();
|
||||
case LONG:
|
||||
return v.longValue();
|
||||
case DOUBLE:
|
||||
return v.doubleValue();
|
||||
}
|
||||
return v;
|
||||
}
|
||||
|
||||
// </editor-fold>
|
||||
// <editor-fold desc="Location">
|
||||
/**
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user