source: sasview/src/sas/sasgui/guiframe/local_perspectives/plotting/AzimutSlicer.py @ 6d7b252b

Last change on this file since 6d7b252b was 5251ec6, checked in by Paul Kienzle <pkienzle@…>, 6 years ago

improved support for py37 in sasgui

  • Property mode set to 100644
File size: 9.5 KB
Line 
1# TODO: the line slicer should listen to all 2DREFRESH events, get the data and slice it
2#       before pushing a new 1D data update.
3#
4# TODO: NEED MAJOR REFACTOR
5#
6import math
7
8import wx
9
10from sas.sasgui.guiframe.events import NewPlotEvent
11from sas.sasgui.guiframe.events import EVT_SLICER_PARS
12
13from .BaseInteractor import _BaseInteractor
14
15class SectorInteractor(_BaseInteractor):
16    """
17    Select an annulus through a 2D plot
18    """
19    def __init__(self, base, axes, color='black', zorder=3):
20        """
21        """
22        _BaseInteractor.__init__(self, base, axes, color=color)
23        self.markers = []
24        self.axes = axes
25        self.qmax = self.base.data2D.xmax
26        self.connect = self.base.connect
27
28        # # Number of points on the plot
29        self.nbins = 20
30        theta1 = 2 * math.pi / 3
31        theta2 = -2 * math.pi / 3
32
33        # Inner circle
34        from .Arc import ArcInteractor
35        self.inner_circle = ArcInteractor(self, self.base.subplot,
36                                          zorder=zorder,
37                                          r=self.qmax / 2.0,
38                                          theta1=theta1,
39                                          theta2=theta2)
40        self.inner_circle.qmax = self.qmax
41        self.outer_circle = ArcInteractor(self, self.base.subplot,
42                                          zorder=zorder + 1,
43                                          r=self.qmax / 1.8,
44                                          theta1=theta1,
45                                          theta2=theta2)
46        self.outer_circle.qmax = self.qmax * 1.2
47        # self.outer_circle.set_cursor(self.base.qmax/1.8, 0)
48        from .Edge import RadiusInteractor
49        self.right_edge = RadiusInteractor(self, self.base.subplot,
50                                           zorder=zorder + 1,
51                                           arc1=self.inner_circle,
52                                           arc2=self.outer_circle,
53                                           theta=theta1)
54        self.left_edge = RadiusInteractor(self, self.base.subplot,
55                                          zorder=zorder + 1,
56                                          arc1=self.inner_circle,
57                                          arc2=self.outer_circle,
58                                          theta=theta2)
59        self.update()
60        self._post_data()
61        # Bind to slice parameter events
62        self.base.parent.Bind(EVT_SLICER_PARS, self._onEVT_SLICER_PARS)
63
64    def _onEVT_SLICER_PARS(self, event):
65        """
66        """
67        # printEVT("AnnulusSlicer._onEVT_SLICER_PARS")
68        event.Skip()
69        if event.type == self.__class__.__name__:
70            self.set_params(event.params)
71            self.base.update()
72
73    def set_layer(self, n):
74        """
75        """
76        self.layernum = n
77        self.update()
78
79    def clear(self):
80        """
81        """
82        self.clear_markers()
83        self.outer_circle.clear()
84        self.inner_circle.clear()
85        self.right_edge.clear()
86        self.left_edge.clear()
87        # self.base.connect.disconnect()
88        self.base.parent.Unbind(EVT_SLICER_PARS)
89
90    def update(self):
91        """
92        Respond to changes in the model by recalculating the profiles and
93        resetting the widgets.
94        """
95        # Update locations
96        if self.inner_circle.has_move:
97            # print "inner circle has moved"
98            self.inner_circle.update()
99            r1 = self.inner_circle.get_radius()
100            r2 = self.outer_circle.get_radius()
101            self.right_edge.update(r1, r2)
102            self.left_edge.update(r1, r2)
103        if self.outer_circle.has_move:
104            # print "outer circle has moved"
105            self.outer_circle.update()
106            r1 = self.inner_circle.get_radius()
107            r2 = self.outer_circle.get_radius()
108            self.left_edge.update(r1, r2)
109            self.right_edge.update(r1, r2)
110        if self.right_edge.has_move:
111            # print "right edge has moved"
112            self.right_edge.update()
113            self.inner_circle.update(theta1=self.right_edge.get_angle(),
114                                     theta2=None)
115            self.outer_circle.update(theta1=self.right_edge.get_angle(),
116                                     theta2=None)
117        if  self.left_edge.has_move:
118            # print "left Edge has moved"
119            self.left_edge.update()
120            self.inner_circle.update(theta1=None,
121                                     theta2=self.left_edge.get_angle())
122            self.outer_circle.update(theta1=None,
123                                     theta2=self.left_edge.get_angle())
124
125    def save(self, ev):
126        """
127        Remember the roughness for this layer and the next so that we
128        can restore on Esc.
129        """
130        self.base.freeze_axes()
131        self.inner_circle.save(ev)
132        self.outer_circle.save(ev)
133        self.right_edge.save(ev)
134        self.left_edge.save(ev)
135
136    def _post_data(self):
137        pass
138
139    def post_data(self, new_sector):
140        """ post data averaging in Q"""
141        if self.inner_circle.get_radius() < self.outer_circle.get_radius():
142            rmin = self.inner_circle.get_radius()
143            rmax = self.outer_circle.get_radius()
144        else:
145            rmin = self.outer_circle.get_radius()
146            rmax = self.inner_circle.get_radius()
147        if self.right_edge.get_angle() < self.left_edge.get_angle():
148            phimin = self.right_edge.get_angle()
149            phimax = self.left_edge.get_angle()
150        else:
151            phimin = self.left_edge.get_angle()
152            phimax = self.right_edge.get_angle()
153        # print "phimin, phimax, rmin ,rmax",math.degrees(phimin),
154        # math.degrees(phimax), rmin ,rmax
155        # from sas.sascalc.dataloader.manipulations import SectorQ
156
157        sect = new_sector(r_min=rmin, r_max=rmax,
158                          phi_min=phimin, phi_max=phimax)
159        sector = sect(self.base.data2D)
160
161        from sas.sasgui.guiframe.dataFitting import Data1D
162        if hasattr(sector, "dxl"):
163            dxl = sector.dxl
164        else:
165            dxl = None
166        if hasattr(sector, "dxw"):
167            dxw = sector.dxw
168        else:
169            dxw = None
170        new_plot = Data1D(x=sector.x, y=sector.y, dy=sector.dy,
171                          dxl=dxl, dxw=dxw)
172        new_plot.name = str(new_sector.__name__) + \
173                        "(" + self.base.data2D.name + ")"
174        new_plot.source = self.base.data2D.source
175        new_plot.interactive = True
176        # print "loader output.detector",output.source
177        new_plot.detector = self.base.data2D.detector
178        # If the data file does not tell us what the axes are, just assume...
179        new_plot.xaxis("\\rm{Q}", 'rad')
180        new_plot.yaxis("\\rm{Intensity} ", "cm^{-1}")
181        new_plot.group_id = str(new_sector.__name__) + self.base.data2D.name
182        self.base.parent.update_theory(data_id=self.base.data2D.id, \
183                                       theory=new_plot)
184        wx.PostEvent(self.base.parent,
185                     NewPlotEvent(plot=new_plot, title=str(new_sector.__name__)))
186
187    def moveend(self, ev):
188        #TODO: why is this empty?
189        pass
190
191    def restore(self):
192        """
193        Restore the roughness for this layer.
194        """
195        self.inner_circle.restore()
196        self.outer_circle.restore()
197        self.right_edge.restore()
198        self.left_edge.restore()
199
200    def move(self, x, y, ev):
201        """
202        Process move to a new position, making sure that the move is allowed.
203        """
204        pass
205
206    def set_cursor(self, x, y):
207        """
208        """
209        pass
210
211    def get_params(self):
212        """
213        """
214        params = {}
215        params["r_min"] = self.inner_circle.get_radius()
216        params["r_max"] = self.outer_circle.get_radius()
217        params["phi_min"] = self.right_edge.get_angle()
218        params["phi_max"] = self.left_edge.get_angle()
219        params["nbins"] = self.nbins
220        return params
221
222    def set_params(self, params):
223        """
224        """
225        # print "setparams on main slicer ",params
226        inner = params["r_min"]
227        outer = params["r_max"]
228        phi_min = params["phi_min"]
229        phi_max = params["phi_max"]
230        self.nbins = int(params["nbins"])
231
232        self.inner_circle.set_cursor(inner, phi_min, phi_max, self.nbins)
233        self.outer_circle.set_cursor(outer, phi_min, phi_max, self.nbins)
234        self.right_edge.set_cursor(inner, outer, phi_min)
235        self.left_edge.set_cursor(inner, outer, phi_max)
236        self._post_data()
237
238    def freeze_axes(self):
239        """
240        """
241        self.base.freeze_axes()
242
243    def thaw_axes(self):
244        """
245        """
246        self.base.thaw_axes()
247
248    def draw(self):
249        """
250        """
251        self.base.draw()
252
253class SectorInteractorQ(SectorInteractor):
254    """
255    """
256    def __init__(self, base, axes, color='black', zorder=3):
257        """
258        """
259        SectorInteractor.__init__(self, base, axes, color=color)
260        self.base = base
261        self._post_data()
262
263    def _post_data(self):
264        """
265        """
266        from sas.sascalc.dataloader.manipulations import SectorQ
267        self.post_data(SectorQ)
268
269
270class SectorInteractorPhi(SectorInteractor):
271    """
272    """
273    def __init__(self, base, axes, color='black', zorder=3):
274        """
275        """
276        SectorInteractor.__init__(self, base, axes, color=color)
277        self.base = base
278        self._post_data()
279
280    def _post_data(self):
281        """
282        """
283        from sas.sascalc.dataloader.manipulations import SectorPhi
284        self.post_data(SectorPhi)
285
Note: See TracBrowser for help on using the repository browser.