fix draw extent in mapaxes

This commit is contained in:
wyq 2024-03-21 09:34:02 +08:00
parent 4eefdbb7da
commit 6266e23081
15 changed files with 116 additions and 44 deletions

View File

@ -757,10 +757,12 @@ public class MapPlot extends Plot2D implements IWebMapPanel {
*/ */
@Override @Override
public void setDrawExtent(Extent extent) { public void setDrawExtent(Extent extent) {
super.setDrawExtent(extent); if (!this.fixDrawExtent) {
super.setDrawExtent(extent);
if (!this.isLonLatMap()) { if (!this.isLonLatMap()) {
((MapGridLine) this.gridLine).setExtent(extent); ((MapGridLine) this.gridLine).setExtent(extent);
}
} }
} }

View File

@ -159,6 +159,15 @@ public class Plot2D extends AbstractPlot2D {
this.graphics.remove(this.graphics.size() - 1); this.graphics.remove(this.graphics.size() - 1);
} }
/**
* Remove last added graphic
*/
public void removeLastAddedGraphic() {
if (this.lastAddedGraphic != null) {
this.graphics.remove(this.lastAddedGraphic);
}
}
/** /**
* Add graphic list * Add graphic list
* *

View File

@ -40,6 +40,7 @@ package org.meteoinfo.geometry.graphic;
protected GeneralPath clipPath; protected GeneralPath clipPath;
protected Graphic clipGraphic; protected Graphic clipGraphic;
private ResizeAbility _resizeAbility = ResizeAbility.RESIZE_ALL; private ResizeAbility _resizeAbility = ResizeAbility.RESIZE_ALL;
protected int handle;
// </editor-fold> // </editor-fold>
// <editor-fold desc="Constructor"> // <editor-fold desc="Constructor">
@ -193,6 +194,22 @@ package org.meteoinfo.geometry.graphic;
return _resizeAbility; return _resizeAbility;
} }
/**
* Get handle
* @return Handle
*/
public int getHandle() {
return this.handle;
}
/**
* Set handle
* @param value Handle
*/
public void setHandle(int value) {
this.handle = value;
}
/** /**
* Get extent * Get extent
* *

View File

@ -1,34 +1,34 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?> <?xml version="1.0" encoding="UTF-8" standalone="no"?>
<MeteoInfo File="milconfig.xml" Type="configurefile"> <MeteoInfo File="milconfig.xml" Type="configurefile">
<Path OpenPath="D:\Working\MIScript\Jython\mis\plot_types\wind"> <Path OpenPath="D:\Working\MIScript\Jython\mis\meteo\wrf">
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\funny"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\plot"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\io\burf"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\meteo"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\chart"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\chart\legend"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\io\geotiff"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\meteo\wrf"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\contour"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\io"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\io\awx"/> <RecentFolder Folder="D:\Working\MIScript\Jython\mis\io\awx"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\weather"/> <RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\weather"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\wind"/> <RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\wind"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\scatter"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\map"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\map\projection"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\io"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\io\grads"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\meteo"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\contour"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\plot_types\plot"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\meteo\eof"/>
<RecentFolder Folder="D:\Working\MIScript\Jython\mis\meteo\wrf"/>
</Path> </Path>
<File> <File>
<OpenedFiles> <OpenedFiles>
<OpenedFile File="D:\Working\MIScript\Jython\mis\meteo\calc\frontogenesis.py"/> <OpenedFile File="D:\Working\MIScript\Jython\mis\meteo\eof\reof_elnino.py"/>
<OpenedFile File="D:\Working\MIScript\Jython\mis\io\awx\awx_fy2g_amv.py"/> <OpenedFile File="D:\Working\MIScript\Jython\mis\meteo\eof\reof_function_hgt.py"/>
<OpenedFile File="D:\Working\MIScript\Jython\mis\plot_types\weather\stationmodel.py"/> <OpenedFile File="D:\Working\MIScript\Jython\mis\plot_types\plot\plot_animation_1.py"/>
<OpenedFile File="D:\Working\MIScript\Jython\mis\plot_types\wind\quiverm_5.py"/> <OpenedFile File="D:\Working\MIScript\Jython\mis\meteo\wrf\wrf_destagger_uv_webmap_loop_1.py"/>
</OpenedFiles> </OpenedFiles>
<RecentFiles> <RecentFiles>
<RecentFile File="D:\Working\MIScript\Jython\mis\meteo\calc\frontogenesis.py"/> <RecentFile File="D:\Working\MIScript\Jython\mis\meteo\eof\reof_elnino.py"/>
<RecentFile File="D:\Working\MIScript\Jython\mis\io\awx\awx_fy2g_amv.py"/> <RecentFile File="D:\Working\MIScript\Jython\mis\meteo\eof\reof_function_hgt.py"/>
<RecentFile File="D:\Working\MIScript\Jython\mis\plot_types\weather\stationmodel.py"/> <RecentFile File="D:\Working\MIScript\Jython\mis\plot_types\plot\plot_animation_1.py"/>
<RecentFile File="D:\Working\MIScript\Jython\mis\plot_types\wind\quiverm_5.py"/> <RecentFile File="D:\Working\MIScript\Jython\mis\meteo\wrf\wrf_destagger_uv_webmap_loop_1.py"/>
</RecentFiles> </RecentFiles>
</File> </File>
<Font> <Font>
@ -36,5 +36,5 @@
</Font> </Font>
<LookFeel DockWindowDecorated="true" LafDecorated="true" Name="FlatDarkLaf"/> <LookFeel DockWindowDecorated="true" LafDecorated="true" Name="FlatDarkLaf"/>
<Figure DoubleBuffering="true"/> <Figure DoubleBuffering="true"/>
<Startup MainFormLocation="-7,-7" MainFormSize="1293,685"/> <Startup MainFormLocation="-7,0" MainFormSize="1396,837"/>
</MeteoInfo> </MeteoInfo>

View File

@ -540,24 +540,37 @@ def eof(x, svd=True, transform=False, return_index=False):
else: else:
return EOF, E, PC return EOF, E, PC
def varimax(x, normalize=False, tol=1e-10, it_max=1000): def varimax(x, norm=True, tol=1e-10, it_max=1000):
""" """
Rotate EOFs according to varimax algorithm Rotate EOFs according to varimax algorithm
:param x: (*array_like*) Input 2-D array. :param x: (*array_like*) Input 2-D array.
:param normalize: (*boolean*) Determines whether to normalize the rows or columns :param norm: (*boolean*) Determines whether to do Kaiser normalization the rows
of the loadings before performing the rotation. of the loadings before performing the rotation. Default is `True`.
:param tol: (*float*) Tolerance. :param tol: (*float*) Tolerance.
:param it_max: (*int*) Specifies the maximum number of iterations to do. :param it_max: (*int*) Specifies the maximum number of iterations to do.
:returns: Rotated EOFs and rotate matrix. :returns: Rotated EOFs and rotate matrix.
""" """
p, nc = x.shape has_nan = False
if x.contains_nan(): #Has NaN value
mask = np.isnan(x).sum(axis=1)
valid_idx = np.where(mask==0)[0]
xx = x[valid_idx,:]
has_nan = True
else:
xx = x.copy()
if norm:
h = np.sqrt(np.sum(xx**2, axis=1))
xx = xx / h[:, None]
p, nc = xx.shape
TT = np.eye(nc) TT = np.eye(nc)
d = 0 d = 0
for _ in range(it_max): for _ in range(it_max):
z = np.dot(x, TT) z = np.dot(xx, TT)
B = np.dot(x.T, (z**3 - np.dot(z, np.diag(np.squeeze(np.dot(np.ones((1,p)), (z**2))))) / p)) B = np.dot(xx.T, (z**3 - np.dot(z, np.diag(np.squeeze(np.dot(np.ones((1,p)), (z**2))))) / p))
U, S, Vh = np.linalg.svd(B) U, S, Vh = np.linalg.svd(B)
TT = np.dot(U, Vh) TT = np.dot(U, Vh)
d2 = d d2 = d
@ -567,5 +580,14 @@ def varimax(x, normalize=False, tol=1e-10, it_max=1000):
break break
# Final matrix. # Final matrix.
r = np.dot(x, TT) r = np.dot(xx, TT)
if norm:
r = r * h[:,None]
if has_nan:
rr = np.ones(x.shape) * np.nan
rr[valid_idx,:] = r
r = rr
return r, TT return r, TT

View File

@ -139,7 +139,7 @@ class DimArray(NDArray):
ylim = [float(ylims[0]), float(ylims[1])] ylim = [float(ylims[0]), float(ylims[1])]
yidx = i yidx = i
if not xlim is None and not ylim is None: if not xlim is None and not ylim is None:
fromproj=KnownCoordinateSystems.geographic.world.WGS1984 fromproj = KnownCoordinateSystems.geographic.world.WGS1984
inpt = PointD(xlim[0], ylim[0]) inpt = PointD(xlim[0], ylim[0])
outpt1 = Reproject.reprojectPoint(inpt, fromproj, self.proj) outpt1 = Reproject.reprojectPoint(inpt, fromproj, self.proj)
inpt = PointD(xlim[1], ylim[1]) inpt = PointD(xlim[1], ylim[1])

View File

@ -747,6 +747,7 @@ class Axes(object):
extent = self._axes.getDrawExtent() extent = self._axes.getDrawExtent()
extent.minX = xmin extent.minX = xmin
extent.maxX = xmax extent.maxX = xmax
self._axes.setFixDrawExtent(False)
self._axes.setDrawExtent(extent) self._axes.setDrawExtent(extent)
self._axes.setExtent(extent.clone()) self._axes.setExtent(extent.clone())
self._axes.setFixDrawExtent(True) self._axes.setFixDrawExtent(True)
@ -775,6 +776,7 @@ class Axes(object):
extent = self._axes.getDrawExtent() extent = self._axes.getDrawExtent()
extent.minY = ymin extent.minY = ymin
extent.maxY = ymax extent.maxY = ymax
self._axes.setFixDrawExtent(False)
self._axes.setDrawExtent(extent) self._axes.setDrawExtent(extent)
self._axes.setExtent(extent.clone()) self._axes.setExtent(extent.clone())
self._axes.setFixDrawExtent(True) self._axes.setFixDrawExtent(True)
@ -1135,13 +1137,14 @@ class Axes(object):
def remove_graphic(self, graphic): def remove_graphic(self, graphic):
""" """
Remove a graphic Remove a graphic.
:param graphic: (*int or Graphic*) The graphic
:return: :param graphic: (*int or Graphic*) The graphic.
""" """
if isinstance(graphic, int): if isinstance(graphic, int):
if graphic < 0: if graphic < 0:
graphic = self._axes.getGraphicNumber() + graphic graphic = self._axes.getGraphicNumber() + graphic
self._axes.getGraphics().remove(graphic) self._axes.getGraphics().remove(graphic)
def remove(self): def remove(self):
@ -1150,6 +1153,19 @@ class Axes(object):
""" """
self._axes.getGraphics().clear() self._axes.getGraphics().clear()
def cll(self):
"""
Remove last graphic.
"""
self._axes.removeLastGraphic()
self.stale = True
def clear(self):
"""
Remove all graphics.
"""
self._axes.getGraphics().clear()
def data2pixel(self, x, y, z=None): def data2pixel(self, x, y, z=None):
""" """
Transform data coordinate to screen coordinate Transform data coordinate to screen coordinate
@ -1504,7 +1520,7 @@ class Axes(object):
:param alpha: (*int*) The alpha blending value, between 0 (transparent) and 1 (opaque). :param alpha: (*int*) The alpha blending value, between 0 (transparent) and 1 (opaque).
:param marker: (*string*) Marker of the points. :param marker: (*string*) Marker of the points.
:param label: (*string*) Label of the point series. :param label: (*string*) Label of the point series.
:param levs: (*array_like*) Optional. A list of floating point numbers indicating the level :param levels: (*array_like*) Optional. A list of floating point numbers indicating the level
points to draw, in increasing order. points to draw, in increasing order.
:returns: Points legend break. :returns: Points legend break.

View File

@ -351,8 +351,10 @@ class MapAxes(Axes):
:param lonlat: (*boolean*) Is longitude/latitude or not. :param lonlat: (*boolean*) Is longitude/latitude or not.
""" """
if limits is None: if limits is None:
self._axes.setFixDrawExtent(False)
self._axes.setDrawExtent(self._axes.getFullExtent()) self._axes.setDrawExtent(self._axes.getFullExtent())
self._axes.setExtent(self._axes.getDrawExtent().clone()) self._axes.setExtent(self._axes.getDrawExtent().clone())
self._axes.setFixDrawExtent(True)
return True return True
else: else:
if len(limits) == 4: if len(limits) == 4:
@ -361,12 +363,14 @@ class MapAxes(Axes):
ymin = limits[2] ymin = limits[2]
ymax = limits[3] ymax = limits[3]
extent = Extent(xmin, xmax, ymin, ymax) extent = Extent(xmin, xmax, ymin, ymax)
self._axes.setFixDrawExtent(False)
if lonlat: if lonlat:
self._axes.setLonLatExtent(extent) self._axes.setLonLatExtent(extent)
self._axes.setExtent(self._axes.getDrawExtent().clone()) self._axes.setExtent(self._axes.getDrawExtent().clone())
else: else:
self._axes.setDrawExtent(extent) self._axes.setDrawExtent(extent)
self._axes.setExtent(extent) self._axes.setExtent(extent)
self._axes.setFixDrawExtent(True)
return True return True
else: else:
print('The limits parameter must be a list with 4 elements: xmin, xmax, ymin, ymax!') print('The limits parameter must be a list with 4 elements: xmin, xmax, ymin, ymax!')
@ -838,6 +842,10 @@ class MapAxes(Axes):
else: else:
graphics = GraphicFactory.createPoints(x._array, y._array, a._array, ls) graphics = GraphicFactory.createPoints(x._array, y._array, a._array, ls)
antialias = kwargs.pop('antialias', None)
if antialias is not None:
graphics.setAntiAlias(antialias)
visible = kwargs.pop('visible', True) visible = kwargs.pop('visible', True)
if visible: if visible:
zorder = kwargs.pop('zorder', None) zorder = kwargs.pop('zorder', None)

View File

@ -1190,12 +1190,10 @@ def cll():
Clear last added plot object. Clear last added plot object.
""" """
if not g_axes is None: if not g_axes is None:
if isinstance(g_axes, MapAxes): g_axes.cll()
g_axes._axes.removeLastLayer() # g_axes._axes.removeLastGraphic()
else: # g_axes._axes.setAutoExtent()
g_axes._axes.removeLastGraphic() # draw_if_interactive()
g_axes._axes.setAutoExtent()
draw_if_interactive()
def clc(): def clc():

View File

@ -35,7 +35,7 @@
<properties> <properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<java.version>1.8</java.version> <java.version>1.8</java.version>
<revision>3.8.1</revision> <revision>3.8.2</revision>
<maven.compiler.source>8</maven.compiler.source> <maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target> <maven.compiler.target>8</maven.compiler.target>
<maven.compiler.release>8</maven.compiler.release> <maven.compiler.release>8</maven.compiler.release>