restart previous running services in onClose event
[enigma2.git] / lib / python / Plugins / SystemPlugins / Satfinder / plugin.py
1 from enigma import eDVBResourceManager,\
2         eDVBFrontendParametersSatellite, eDVBFrontendParameters
3
4 from Screens.Screen import Screen
5 from Screens.ScanSetup import ScanSetup
6 from Screens.MessageBox import MessageBox
7 from Plugins.Plugin import PluginDescriptor
8
9 from Components.Label import Label
10 from Components.Sources.FrontendStatus import FrontendStatus
11 from Components.ActionMap import ActionMap
12 from Components.NimManager import nimmanager, getConfigSatlist
13 from Components.MenuList import MenuList
14 from Components.config import ConfigSelection, getConfigListEntry
15
16 class Tuner:
17         def __init__(self, frontend):
18                 self.frontend = frontend
19                 
20         def tune(self, transponder):
21                 if self.frontend:
22                         print "tuning to transponder with data", transponder
23                         parm = eDVBFrontendParametersSatellite()
24                         parm.frequency = transponder[0] * 1000
25                         parm.symbol_rate = transponder[1] * 1000
26                         parm.polarisation = transponder[2]
27                         parm.fec = transponder[3]
28                         parm.inversion = transponder[4]
29                         parm.orbital_position = transponder[5]
30                         parm.system = 0  # FIXMEE !! HARDCODED DVB-S (add support for DVB-S2)
31                         parm.modulation = 1 # FIXMEE !! HARDCODED QPSK 
32                         feparm = eDVBFrontendParameters()
33                         feparm.setDVBS(parm)
34                         self.lastparm = feparm
35                         self.frontend.tune(feparm)
36         
37         def retune(self):
38                 if self.frontend:
39                         self.frontend.tune(self.lastparm)
40
41 class Satfinder(ScanSetup):
42         skin = """
43                 <screen position="90,100" size="520,400" title="Tune">
44                         <widget name="config" position="20,10" size="460,210" scrollbarMode="showOnDemand" />
45                         <widget name="introduction" position="20,360" zPosition="-10" size="350,30" font="Regular;23" />
46                         <eLabel text="dB:" position="23,230" size="60,22" font="Regular;21" />
47                         <eLabel text="SNR:" position="23,255" size="60,22" font="Regular;21" />
48                         <eLabel text="AGC:" position="23,280" size="60,22" font="Regular;21" />
49                         <eLabel text="BER:" position="23,305" size="60,22" font="Regular;21" />
50                         <eLabel text="Lock:" position="23,330" size="60,22" font="Regular;21" />
51                         <widget source="Frontend" render="Label" position="295,230" size="60,22" font="Regular;21" >
52                                 <convert type="FrontendInfo">SNRdB</convert>
53                         </widget>
54                         <widget source="Frontend" render="Label" position="295,255" size="60,22" font="Regular;21" >
55                                 <convert type="FrontendInfo">SNR</convert>
56                         </widget>
57                         <widget source="Frontend" render="Label" position="295,280" size="60,22" font="Regular;21" >
58                                 <convert type="FrontendInfo">AGC</convert>
59                         </widget>
60                         <widget source="Frontend" render="Label" position="295,305" size="60,22" font="Regular;21" >
61                                 <convert type="FrontendInfo">BER</convert>
62                         </widget>
63                         <widget source="Frontend" render="Progress" position="85,257" size="200,22" >
64                                 <convert type="FrontendInfo">SNR</convert>
65                         </widget>
66                         <widget source="Frontend" render="Progress" position="85,282" size="200,22" >
67                                 <convert type="FrontendInfo">AGC</convert>
68                         </widget>
69                         <widget source="Frontend" render="Progress" position="85,307" size="200,22" >
70                                 <convert type="FrontendInfo">BER</convert>
71                         </widget>
72                         <widget source="Frontend" render="Pixmap" pixmap="skin_default/buttons/key_green.png" position="295,330" zPosition="4" size="28,20" alphatest="on" >
73                                 <convert type="FrontendInfo">LOCK</convert>
74                         <convert type="ConditionalShowHide" />
75                         </widget>
76                         <widget source="Frontend" render="Pixmap" pixmap="skin_default/buttons/key_red.png" position="295,330" zPosition="4" size="28,20" alphatest="on" >
77                                 <convert type="FrontendInfo">LOCK</convert>
78                         <convert type="ConditionalShowHide">Invert</convert>
79                         </widget>
80                 </screen>"""
81
82         def openFrontend(self):
83                 res_mgr = eDVBResourceManager.getInstance()
84                 if res_mgr:
85                         self.raw_channel = res_mgr.allocateRawChannel(self.feid)
86                         if self.raw_channel:
87                                 self.frontend = self.raw_channel.getFrontend()
88                                 if self.frontend:
89                                         return True
90                                 else:
91                                         print "getFrontend failed"
92                         else:
93                                 print "getRawChannel failed"
94                 else:
95                         print "getResourceManager instance failed"
96                 return False
97
98         def __init__(self, session, feid):
99                 self.initcomplete = False
100                 self.feid = feid
101                 self.oldref = None
102
103                 if not self.openFrontend():
104                         self.oldref = session.nav.getCurrentlyPlayingServiceReference()
105                         session.nav.stopService() # try to disable foreground service
106                         if not self.openFrontend():
107                                 if session.pipshown: # try to disable pip
108                                         session.pipshown = False
109                                         del session.pip
110                                         if not self.openFrontend():
111                                                 self.frontend = None # in normal case this should not happen
112
113                 ScanSetup.__init__(self, session)
114                 self.tuner = Tuner(self.frontend)
115                 self["introduction"].setText("")
116                 self["Frontend"] = FrontendStatus(frontend_source = lambda : self.frontend, update_interval = 100)
117                 self.initcomplete = True
118                 self.onClose.append(self.__onClose)
119
120         def __onClose(self):
121                 self.session.nav.playService(self.oldref)
122
123         def createSetup(self):
124                 self.typeOfTuningEntry = None
125                 self.satEntry = None
126                 
127                 self.list = []
128                 self.typeOfTuningEntry = getConfigListEntry(_('Tune'), self.tuning_type)
129                 self.list.append(self.typeOfTuningEntry)
130                 self.satEntry = getConfigListEntry(_('Satellite'), self.tuning_sat)
131                 self.list.append(self.satEntry)
132                 if self.tuning_type.value == "manual_transponder":
133                         self.list.append(getConfigListEntry(_('Frequency'), self.scan_sat.frequency))
134                         self.list.append(getConfigListEntry(_('Inversion'), self.scan_sat.inversion))
135                         self.list.append(getConfigListEntry(_('Symbol Rate'), self.scan_sat.symbolrate))
136                         self.list.append(getConfigListEntry(_("Polarity"), self.scan_sat.polarization))
137                         self.list.append(getConfigListEntry(_("FEC"), self.scan_sat.fec))
138                 elif self.tuning_transponder and self.tuning_type.value == "predefined_transponder":
139                         self.list.append(getConfigListEntry(_("Transponder"), self.tuning_transponder))
140                 self["config"].list = self.list
141                 self["config"].l.setList(self.list)
142
143         def newConfig(self):
144                 if self["config"].getCurrent() == self.typeOfTuningEntry:
145                         self.createSetup()
146                 elif self["config"].getCurrent() == self.satEntry:
147                         self.updateSats()
148                         self.createSetup()
149
150         def sat_changed(self, config_element):
151                 self.newConfig()
152                 self.retune(config_element)
153
154         def retune(self, configElement):
155                 returnvalue = (0, 0, 0, 0, 0, 0, 0)
156                 satpos = self.tuning_sat.orbital_position
157                 
158                 if satpos is not None:
159                         if self.tuning_type.value == "manual_transponder":
160                                 returnvalue = (self.scan_sat.frequency.value, self.scan_sat.symbolrate.value, self.scan_sat.polarization.index, self.scan_sat.fec.index, self.scan_sat.inversion.index, satpos)
161                         elif self.tuning_type.value == "predefined_transponder":
162                                 transponder = nimmanager.getTransponders(satpos)[self.tuning_transponder.index]
163                                 returnvalue = (int(transponder[1] / 1000), int(transponder[2] / 1000), transponder[3], transponder[4], 2, satpos)
164                         self.tune(returnvalue)
165
166         def createConfig(self, foo):
167                 self.tuning_transponder = None
168                 self.tuning_type = ConfigSelection(choices = [("manual_transponder", _("Manual transponder")), ("predefined_transponder", _("Predefined transponder"))])
169                 self.tuning_sat = getConfigSatlist(192, nimmanager.getSatListForNim(self.feid))
170                 ScanSetup.createConfig(self, None)
171                 
172                 self.updateSats()
173                 
174                 self.tuning_type.addNotifier(self.retune, initial_call = False)
175                 self.tuning_sat.addNotifier(self.sat_changed, initial_call = False)
176                 self.scan_sat.frequency.addNotifier(self.retune, initial_call = False)
177                 self.scan_sat.inversion.addNotifier(self.retune, initial_call = False)
178                 self.scan_sat.symbolrate.addNotifier(self.retune, initial_call = False)
179                 self.scan_sat.polarization.addNotifier(self.retune, initial_call = False)
180                 self.scan_sat.fec.addNotifier(self.retune, initial_call = False)
181
182         def updateSats(self):
183                 orb_pos = self.tuning_sat.orbital_position
184                 if orb_pos is not None:
185                         transponderlist = nimmanager.getTransponders(orb_pos)
186                         list = []
187                         for x in transponderlist:
188                                 if x[3] == 0:
189                                         pol = "H"
190                                 elif x[3] == 1:
191                                         pol = "V"
192                                 elif x[3] == 2:
193                                         pol = "CL"
194                                 elif x[3] == 3:
195                                         pol = "CR"
196                                 else:
197                                         pol = "??"
198                                 if x[4] == 0:
199                                         fec = "FEC_AUTO"
200                                 elif x[4] == 1:
201                                         fec = "FEC_1_2"
202                                 elif x[4] == 2:
203                                         fec = "FEC_2_3"
204                                 elif x[4] == 3:
205                                         fec = "FEC_3_4"
206                                 elif x[4] == 4:
207                                         fec = "FEC_5_6"
208                                 elif x[4] == 5:
209                                         fec = "FEC_7_8"
210                                 elif x[4] == 6:
211                                         fec = "FEC_8_9"
212                                 elif x[4] == 7:
213                                         fec = "FEC_3_5"
214                                 elif x[4] == 8:
215                                         fec = "FEC_4_5"
216                                 elif x[4] == 9:
217                                         fec = "FEC_9_10"
218                                 elif x[4] == 15:
219                                         fec = "FEC_None"
220                                 else:
221                                         fec = "FEC_Unknown"
222                                 list.append(str(x[1]) + "," + str(x[2]) + "," + pol + "," + fec)
223                         self.tuning_transponder = ConfigSelection(choices = list)
224                         self.tuning_transponder.addNotifier(self.retune, initial_call = False)
225
226         def keyGo(self):
227                 self.retune(self.tuning_type)
228
229         def restartPrevService(self, yesno):
230                 if yesno:
231                         if self.frontend:
232                                 self.frontend = None
233                                 del self.raw_channel
234                 else:
235                         self.oldref = None
236                 self.close(None)
237
238         def keyCancel(self):
239                 if self.oldref:
240                         self.session.openWithCallback(self.restartPrevService, MessageBox, _("Zap back to service before satfinder?"), MessageBox.TYPE_YESNO)
241                 else:
242                         self.restartPrevService(False)
243
244         def tune(self, transponder):
245                 if self.initcomplete:
246                         if transponder is not None:
247                                 self.tuner.tune(transponder)
248
249 class NimSelection(Screen):
250         skin = """
251                 <screen position="140,165" size="400,100" title="select Slot">
252                         <widget name="nimlist" position="20,10" size="360,75" />
253                 </screen>"""
254                 
255         def __init__(self, session):
256                 Screen.__init__(self, session)
257
258                 nimlist = nimmanager.getNimListOfType("DVB-S")
259                 nimMenuList = []
260                 for x in nimlist:
261                         nimMenuList.append((nimmanager.nim_slots[x].friendly_full_description, x))
262
263                 self["nimlist"] = MenuList(nimMenuList)
264
265                 self["actions"] = ActionMap(["OkCancelActions"],
266                 {
267                         "ok": self.okbuttonClick ,
268                         "cancel": self.close
269                 }, -1)
270
271         def okbuttonClick(self):
272                 selection = self["nimlist"].getCurrent()[1]
273                 self.session.open(Satfinder, selection)
274
275 def SatfinderMain(session, **kwargs):
276         nimList = nimmanager.getNimListOfType("DVB-S")
277         if len(nimList) == 0:
278                 session.open(MessageBox, _("No satellite frontend found!!"), MessageBox.TYPE_ERROR)
279         else:
280                 if session.nav.RecordTimer.isRecording():
281                         session.open(MessageBox, _("A recording is currently running. Please stop the recording before trying to start the satfinder."), MessageBox.TYPE_ERROR)
282                 else:
283                         if len(nimList) == 1:
284                                 session.open(Satfinder, nimList[0])
285                         else:
286                                 session.open(NimSelection)
287
288 def SatfinderStart(menuid, **kwargs):
289         if menuid == "scan":
290                 return [(_("Satfinder"), SatfinderMain, "satfinder", None)]
291         else:
292                 return []
293
294 def Plugins(**kwargs):
295         if (nimmanager.hasNimType("DVB-S")):
296                 return PluginDescriptor(name=_("Satfinder"), description="Helps setting up your dish", where = PluginDescriptor.WHERE_MENU, fnc=SatfinderStart)
297         else:
298                 return []