TMenu.py 29 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863
  1. # -*- coding:utf-8 -*-
  2. import time
  3. from BaseLog import CBaseLog
  4. from ExtraData import CExtraData
  5. from OptionExcel import COptionExcel
  6. from OptionConfig import COptionConfig
  7. from OptionAction import COptionAction
  8. from ssat_sdk.source_input import SourceGenInput
  9. from ssat_sdk.tv_detect import *
  10. from ssat_sdk.device_manage.capturecard_manager import CCardManager
  11. from ssat_sdk.utils.string_util import strcmp
  12. # 测试使用到
  13. import random
  14. class CTMenu(CBaseLog):
  15. sourceInput = SourceGenInput()
  16. # 红老鼠遥控对象;
  17. redRat3 = TvOperator()
  18. # 创建视频采集对象
  19. captureCard = CCardManager()
  20. # 图片切割对象
  21. imgCMP = ImageCMP()
  22. rgbColor = RGBColor()
  23. CIE = CIEluvCaculator()
  24. def __init__(self, ocrDict=None):
  25. CBaseLog.__init__(self)
  26. self.__exData = CExtraData()
  27. self.__optionExcel = COptionExcel(self.__exData)
  28. self.__optionConfig = COptionConfig(self.__exData, self.__optionExcel)
  29. self.__curOpa = None
  30. self.__lastOpa = None
  31. self.__lastTime = None
  32. @property
  33. def exData(self):
  34. return self.__exData
  35. @property
  36. def optionExcel(self):
  37. return self.__optionExcel
  38. @property
  39. def optionConfig(self):
  40. return self.__optionConfig
  41. @property
  42. def opa(self):
  43. return self.__curOpa
  44. @property
  45. def pos(self):
  46. return self.__curOpa.pos
  47. def setOpa(self, opa):
  48. self.__curOpa = opa
  49. def setCurPos(self, pos):
  50. self.__curOpa.setCurPos(pos)
  51. def clearOpa(self):
  52. self.__lastOpa = None
  53. self.__curOpa = None
  54. '''
  55. 函数:同步两个opa信息;
  56. 参数:
  57. 返回:
  58. '''
  59. def SyncOptionInfo(self):
  60. # 如果上次同步超过5秒,认为菜单退出; 意义不大
  61. # if self.__lastTime and time.time() - self.__lastTime > 5:
  62. # self.info(u"前后两次同步时间差超过5秒")
  63. # self.__lastOpa = None
  64. if self.__lastOpa:
  65. self.info(u"lastOpa.pos=%d" % self.__lastOpa.pos)
  66. diffValue = self.__lastOpa.pos - self.__curOpa.getPathLength()
  67. # 前者位置大于当前opa长度;
  68. if diffValue == 0:
  69. if self.__curOpa.isOptionInPaths(self.__lastOpa.pos, self.__lastOpa.optionValue) is True:
  70. self.__curOpa.setCurPos(self.__lastOpa.pos)
  71. elif diffValue > 0:
  72. # 判断路径是否为子集关系;
  73. if self.__lastOpa.isOptionInPaths(self.__lastOpa.getPathLength(), self.__curOpa.curOptionName) is True:
  74. while diffValue > 0:
  75. diffValue -= 1
  76. self.__lastOpa.back2ParentNode()
  77. # 同时设置当前opa位置;
  78. self.__curOpa.setCurPos(self.__curOpa.getPathLength())
  79. elif diffValue < 0:
  80. # 判断路径是否为子集关系;
  81. if self.__curOpa.isOptionInPaths(self.__lastOpa.pos, self.__lastOpa.curOptionName) is True:
  82. self.__curOpa.setCurPos(self.__lastOpa.pos)
  83. # 记录;
  84. # self.__lastTime = time.time()
  85. self.__lastOpa = self.__curOpa
  86. def takePicture(self):
  87. img = os.path.join(getSATTmpDIR(), "menutree_runpath.png")
  88. self.captureCard.takePicture(img)
  89. if not os.path.exists(img):
  90. self.error(u"截图失败:%s" % img)
  91. return img
  92. '''
  93. 函数:判断两值(for_ocr与ocr识别结果)是否相等;
  94. 参数:
  95. srcValue 源值,excel表格中读取的value值。
  96. tagValue 目标值,ocr识别的结果值。
  97. 返回:相同返回True。
  98. '''
  99. def __isValueEqual(self, srcValue, tagValue):
  100. self.info(u"源值=%s, 目标值=%s" % (str(srcValue), str(tagValue)))
  101. '''
  102. 函数:移动到目标节点上(路径节点和value节点)
  103. 参数:
  104. opa COptionAction对象;
  105. moveDirection 移动方向,True表示调用move_key[1](向下或向右), False表示调用move_key[0]。
  106. maxTry 最大移动次数,防止死循环。
  107. 返回:Boolean是否在目标节点上, 文本或数值。
  108. '''
  109. def __move2TargetNode(self, opa, moveDirection, maxTry=15):
  110. tryCount = 0
  111. # 是否到目标结点了;
  112. isOnTargetNode = False
  113. # 目标节点聚焦状态;
  114. targetFocus = False
  115. # 目标文本或数值;
  116. targetText = None
  117. # 移动到目标节点;
  118. while True:
  119. # 判断是否移动成功;
  120. targetFocus, targetText = opa.isOnTargetNode()
  121. if targetFocus is True:
  122. # 如果已在目标结点,退出循环;
  123. if opa.isOnTargetOption() or opa.isOnValueSheet():
  124. self.info(u"<到达目标路径节点或value节点>")
  125. isOnTargetNode = True
  126. break
  127. # 未到目标,进入下一节点;
  128. self.info(u"<进入下一节点>")
  129. opa.enterNode()
  130. # 先处理密码框;
  131. hasBox, dealStatus = opa.dealPasswordBox()
  132. if hasBox is True and dealStatus is False:
  133. break
  134. continue
  135. # endif
  136. # 移动到下/上一节点;
  137. if moveDirection:
  138. opa.move2NextSiblingNode()
  139. else:
  140. opa.move2PrevSiblingNode()
  141. tryCount += 1
  142. if tryCount > maxTry:
  143. self.warn(u"已%s遍历超过%d次,仍未找到焦点" % ("正向" if moveDirection else "逆向", maxTry))
  144. break
  145. # end-while
  146. return isOnTargetNode, targetText
  147. def move2TargetNode(self, opa, moveDirection, maxTry=15):
  148. return self.__move2TargetNode(opa, moveDirection, maxTry)
  149. def back2Home(self):
  150. return self.__back2Home(self.__curOpa)
  151. '''
  152. 函数:退出 usb 信源界面;
  153. 参数:
  154. opa COptionAction对象;
  155. 返回:如果可以直接调用信源菜单返回True,否则返回False;
  156. '''
  157. def __exitUsbSource(self, opa):
  158. # 有些信源,需要手动enter
  159. enterKey = opa.curOptionInfo['enter_key']
  160. # 因为信源界面消失了,需要再调用一次.
  161. opa.callFirstOptionShortCutKey()
  162. # 判断是否聚焦成功;
  163. if opa.isOnFirstOption() is True:
  164. return True
  165. self.redRat3.sendKey("ok", duration=2)
  166. # 因为信源界面消失了,需要再调用一次.
  167. opa.callFirstOptionShortCutKey()
  168. # 判断是否聚焦成功;
  169. if opa.isOnFirstOption() is True:
  170. self.redRat3.sendKey("ok", duration=2)
  171. return False
  172. self.redRat3.sendKey("exit", duration=2)
  173. # 因为信源界面消失了,需要再调用一次.
  174. opa.callFirstOptionShortCutKey()
  175. # 判断是否聚焦成功;
  176. if opa.isOnFirstOption() is True:
  177. self.redRat3.sendKey("ok", duration=2)
  178. return False
  179. self.redRat3.sendKey("return", duration=2)
  180. # 因为信源界面消失了,需要再调用一次.
  181. opa.callFirstOptionShortCutKey()
  182. # 判断是否聚焦成功;
  183. if opa.isOnFirstOption() is True:
  184. self.redRat3.sendKey("ok", duration=2)
  185. return False
  186. '''
  187. 函数:移动到目标信源节点上。
  188. 参数:
  189. opa COptionAction对象;
  190. moveDirection 移动方向,True表示调用move_key[1](向下或向右), False表示调用move_key[0]。
  191. maxTry 最大移动次数,防止死循环。
  192. 返回:Boolean是否在目标节点上, 文本或数值。
  193. '''
  194. def __move2SourceNode(self, opa, moveDirection, maxTry=15):
  195. tryCount = 0
  196. # 目标节点聚焦状态;
  197. targetFocus = False
  198. # 目标文本或数值;
  199. targetText = None
  200. self.info(u"===========maxTry=%d" % maxTry)
  201. # 移动到目标节点;
  202. while True:
  203. # 截图,截图完后马上进入信源;
  204. pic = self.takePicture()
  205. # 有些信源,需要手动enter
  206. enterKey = opa.curOptionInfo['enter_key']
  207. if enterKey != "default":
  208. opa.executeKey(enterKey)
  209. # 判断是否移动成功;
  210. targetFocus, targetText = opa.isOnTargetNode(pic)
  211. if targetFocus is True:
  212. self.info(u"===========到达目标信源节点===========")
  213. break
  214. # endif
  215. # 如果是usb信源,特殊处理;
  216. if targetText and 'usb' in targetText.lower():
  217. if not self.__exitUsbSource(opa):
  218. self.info(u"///////////////////////退出USB成功。///////////////////////")
  219. # 因为信源界面消失了,需要再调用一次.
  220. opa.callFirstOptionShortCutKey()
  221. # 2次:移动到下/上一节点;
  222. opa.move2NextSiblingNode() if moveDirection else opa.move2PrevSiblingNode()
  223. opa.move2NextSiblingNode() if moveDirection else opa.move2PrevSiblingNode()
  224. opa.executeKey(enterKey)
  225. # 因为信源界面消失了,需要再调用一次.
  226. opa.callFirstOptionShortCutKey()
  227. continue
  228. # 因为信源界面消失了,需要再调用一次.
  229. opa.callFirstOptionShortCutKey()
  230. # 移动到下/上一节点;
  231. opa.move2NextSiblingNode() if moveDirection else opa.move2PrevSiblingNode()
  232. tryCount += 1
  233. if tryCount > maxTry:
  234. self.warn(u"已%s遍历超过%d次,仍未找到焦点" % ("正向" if moveDirection else "逆向", maxTry))
  235. break
  236. # end-while
  237. return targetFocus, targetText
  238. '''
  239. 函数:聚焦到指定option中。
  240. 参数:
  241. opa COptionAction对象。
  242. 返回:Boolean,成功返回True.
  243. '''
  244. def __focusOption(self, opa):
  245. # 检测路径是否有效;
  246. if opa.checkRunOptionPath() is False:
  247. self.__back2Home(opa)
  248. return False
  249. # 只有从0层开始才需要调用根菜单;
  250. if self.__curOpa.pos == 0:
  251. # 首先,调用根菜单;
  252. opa.callFirstOptionShortCutKey()
  253. # time.sleep(1)
  254. if opa.isOnFirstOption() is False:
  255. self.error(u"未聚焦到根节点上,退出")
  256. self.__back2Home(opa)
  257. return False
  258. # 遍历到目标option中;
  259. if self.__move2TargetNode(opa, True)[0] is False:
  260. if self.__move2TargetNode(opa, False)[0] is False:
  261. self.__back2Home(opa)
  262. return False
  263. return True
  264. '''
  265. 函数:进入到指定的option中。
  266. 参数:
  267. opa COptionAction对象。
  268. 返回:Boolean,成功返回True.
  269. '''
  270. def __openOption(self, opa):
  271. if self.__focusOption(opa) is False:
  272. return False
  273. # 到达目标option后;
  274. self.info(u"进入option")
  275. opa.enterNode()
  276. # 先处理密码框;
  277. hasBox, dealStatus = opa.dealPasswordBox()
  278. if hasBox is True and dealStatus is False:
  279. self.error(u"密码框处理失败")
  280. return False
  281. return True
  282. '''
  283. 函数:返回到主页(不一定就是Home页,一般指返回运行前的那个画面)
  284. 参数:
  285. opa COptionAction对象;
  286. 返回:
  287. '''
  288. def __back2Home(self, opa):
  289. self.info(u"返回主页")
  290. while opa.pos > 0:
  291. opa.back2ParentNode()
  292. self.info(u"【如果设置value时,会自动回退到上一层父节点,此处操作正常。否则要多返回一层。】")
  293. # value层的enter_key,如果按了ok会返回父层,则少退出一层return。但是目前menutree要兼容适配的旧问题,只能多退出一次。
  294. # 如果未来出现了新的机芯,多按return键会导致退出,需要把这个机制完善
  295. self.redRat3.sendKey("return", 1, 1)
  296. '''
  297. 函数:设置指定的option的值为optionValue。
  298. 参数:
  299. optionName 要设置的option;
  300. optionValue option要设置的值;
  301. 返回: Boolean。
  302. '''
  303. def setOptionValue(self, optionName, optionValue):
  304. self.info(u"【%s】【%s】" % (optionName, optionValue))
  305. CTMenu.sourceInput.setPattern(11)
  306. self.__curOpa = COptionAction(optionName, optionValue, self.__optionConfig, self.__optionExcel)
  307. # 检测路径是否有效;
  308. if self.__openOption(self.__curOpa) is False:
  309. return False
  310. # 遍历到value节点中;
  311. if self.__move2TargetNode(self.__curOpa, True)[0] is False:
  312. if self.__move2TargetNode(self.__curOpa, False)[0] is False:
  313. self.__back2Home(self.__curOpa)
  314. return False
  315. # 找到value节点,设置值;
  316. self.info(u"设置value值:一般只适用于Number类型或Input类型,不适合选择类型。但都必须调用,因为里面有enterkey操作")
  317. self.__curOpa.setOptionValue()
  318. # 返回主页;
  319. self.__back2Home(self.__curOpa)
  320. return True
  321. '''
  322. 函数:移动到目标option后,读取该option的value值,与optionValue进行比较,相等表示检测值与目标值一致;
  323. 参数:
  324. optionName 要设置的option;
  325. optionValue option要设置的值;
  326. 返回: Boolean。
  327. '''
  328. def checkOptionValue(self, optionName, optionValue):
  329. self.info(u"【%s】【%s】" % (optionName, optionValue))
  330. CTMenu.sourceInput.setPattern(11)
  331. self.__curOpa = COptionAction(optionName, optionValue, self.__optionConfig, self.__optionExcel)
  332. # 进入节点;
  333. if self.__openOption(self.__curOpa) is False:
  334. return False
  335. isValueEqual = False
  336. # 获取value节点值;
  337. valueFocus, valueText = self.__curOpa.isOnTargetNode()
  338. self.info(u"===当前捕获的文本内容=%s,目标文本=%s,状态:%d===" % (str(valueText), str(optionValue), valueFocus))
  339. # 如果是数值,则判断获取的值是否相等;否则,只判断是否聚焦.
  340. if type(optionValue) == int or type(optionValue) == float:
  341. isValueEqual = True if float(optionValue) == float(valueText) else False
  342. else:
  343. isValueEqual = valueFocus
  344. # 返回主页;
  345. self.__back2Home(self.__curOpa)
  346. # 聚焦状态就是结果;
  347. self.info(
  348. u"checkOptionValue结果:optionValue=%s, ocrValue=%s, 结果=%d" % (str(optionValue), str(valueText), isValueEqual))
  349. return isValueEqual
  350. '''
  351. 函数:进入指定的option,并且不返回主页。
  352. 参数:
  353. optionName 指定要进入的option节点。
  354. 返回:Boolean。成功进入返回True.
  355. '''
  356. def openOption(self, optionName):
  357. self.info(u"【%s】" % optionName)
  358. CTMenu.sourceInput.setPattern(11)
  359. self.__curOpa = COptionAction(optionName, None, self.__optionConfig, self.__optionExcel)
  360. # 同步前后信息;
  361. self.SyncOptionInfo()
  362. if self.__openOption(self.__curOpa) is False:
  363. return False
  364. # 聚焦状态就是结果;
  365. self.info(u"成功open指定option=%s" % optionName)
  366. return True
  367. '''
  368. 函数:设置self.__curOpa的值;
  369. 参数:
  370. 返回:
  371. 注意:一般在使用了openOption后,才调用该函数.且该函数不返回(不调用back2Home);
  372. '''
  373. def setValue(self, optionValue):
  374. self.info(u"开始设置值:optionName=%s, optionValue=%s" % (self.__curOpa.curOptionName, str(optionValue)))
  375. if self.__curOpa.setValue(optionValue) is False:
  376. self.info(u"该value[%s]不存在" % optionValue)
  377. return False
  378. # 遍历到value节点中;
  379. if self.__move2TargetNode(self.__curOpa, True)[0] is False:
  380. if self.__move2TargetNode(self.__curOpa, False)[0] is False:
  381. self.__back2Home(self.__curOpa)
  382. return False
  383. # 找到value节点,设置值;
  384. self.info(u"设置value值:一般只适用于Number类型或Input类型,不适合选择类型。但都必须调用,因为里面有enterkey操作")
  385. self.__curOpa.setOptionValue()
  386. return True
  387. '''
  388. 函数:聚焦到指定option的value上,不设置不打开不返回。
  389. 参数:
  390. optionName
  391. optionValue
  392. 返回:
  393. 注意:如果optionValue是数值类型,将不会变更值。
  394. 如optionValue=10,实现该optionName的value是100,则不变更其值。
  395. '''
  396. def focusOptionValue(self, optionName, optionValue):
  397. self.info(u"【%s】【%s】" % (optionName, optionValue))
  398. CTMenu.sourceInput.setPattern(11)
  399. self.__curOpa = COptionAction(optionName, optionValue, self.__optionConfig, self.__optionExcel)
  400. # 进入节点;
  401. if self.__openOption(self.__curOpa) is False:
  402. return False
  403. # 遍历到value节点中;
  404. if self.__move2TargetNode(self.__curOpa, True)[0] is False:
  405. if self.__move2TargetNode(self.__curOpa, False)[0] is False:
  406. self.__back2Home(self.__curOpa)
  407. return False
  408. return True
  409. '''
  410. 函数:获取当前option节点的value值。
  411. 参数:
  412. optionName 要获取值的option;
  413. 返回:Boolean, str/int/float
  414. '''
  415. def getOptionValue(self, optionName):
  416. self.info(u"【%s】" % optionName)
  417. CTMenu.sourceInput.setPattern(11)
  418. self.__curOpa = COptionAction(optionName, None, self.__optionConfig, self.__optionExcel)
  419. # 检测路径是否有效;
  420. if self.__openOption(self.__curOpa) is False:
  421. return False, None
  422. # 获取value节点值;
  423. valueFocus, valueText = self.__curOpa.isOnTargetNode()
  424. self.info(u"===当前捕获的文本内容=%s,聚焦状态:%d===" % (str(valueText), valueFocus))
  425. # 返回主页;
  426. self.__back2Home(self.__curOpa)
  427. return valueFocus, valueText
  428. '''
  429. 函数:
  430. 参数:
  431. 返回:
  432. '''
  433. def focusOption(self, optionName):
  434. self.info(u"【%s】" % optionName)
  435. CTMenu.sourceInput.setPattern(11)
  436. self.__curOpa = COptionAction(optionName, None, self.__optionConfig, self.__optionExcel)
  437. return self.__focusOption(self.__curOpa)
  438. '''
  439. 函数:
  440. 参数:
  441. 返回:
  442. '''
  443. def inputUnlock(self, stdText, password=''):
  444. self.__curOpa = COptionAction(None, None, self.__optionConfig, self.__optionExcel)
  445. return self.__curOpa.inputUnlock(stdText, password)
  446. '''
  447. 函数:当焦点已经在option层级上时,移动到指定的option上。
  448. 参数:
  449. optionName 目标option.
  450. 返回:Boolean,成功移动到目标节点返回True。
  451. 注意:该函数不是从根节点开始移动到目标节点,而是假定焦点已经在目标节点层级菜单上。
  452. '''
  453. def moveToOption(self, optionName):
  454. self.__curOpa = COptionAction(optionName, None, self.__optionConfig, self.__optionExcel)
  455. # 已经在该层级上.
  456. self.__curOpa.setCurPos(self.__curOpa.getPathLength() - 1)
  457. # 检测路径是否有效;
  458. if self.__curOpa.checkRunOptionPath() is False:
  459. self.__back2Home(self.__curOpa)
  460. return False
  461. # 遍历到目标option中;
  462. if self.__move2TargetNode(self.__curOpa, True)[0] is False:
  463. if self.__move2TargetNode(self.__curOpa, False)[0] is False:
  464. self.__back2Home(self.__curOpa)
  465. return False
  466. self.info(u"已移动到目标节点[%s]" % optionName)
  467. return True
  468. '''
  469. 函数:检测输入的频道列表,是否都存在,返回不存在的频道列表。
  470. 参数:
  471. channelList 要检测的目标频道列表。
  472. 返回:Boolean, []
  473. 如果有频道没找到,返回False,并返回没找到的频道列表。如果全部找到返回True。
  474. '''
  475. def checkChannelList(self, channelList, maxTry=15):
  476. failChannelList = []
  477. checkResult = True
  478. if not channelList:
  479. self.error(u"传入的待检测的频道列表为空!")
  480. return False, failChannelList
  481. for channel in channelList:
  482. isSearched = self.checkOptionValue("ok", channel)
  483. if not isSearched:
  484. self.warn(u"频道:%s查找失败!" % str(channel))
  485. failChannelList.append(channel)
  486. checkResult = False
  487. # 部分机芯项目(如6586外协松下)按return键无法退出频道,故改为exit键
  488. # self.redRat3.sendKey("return")
  489. self.redRat3.sendKey("exit")
  490. else:
  491. self.info(u"频道:%s查找成功!" % str(channel))
  492. self.redRat3.sendKey("exit")
  493. self.info(u"频道列表检测结果checkResult:%s,检测失败频道列表failChannelLis:%s" % (str(checkResult), str(failChannelList)))
  494. return checkResult, failChannelList
  495. '''
  496. 函数:移动到黑屏的频道。
  497. 参数:
  498. channelCount 要查找多少次频道。
  499. blackThreshold 黑屏阈值。
  500. blackRate 黑屏比率。
  501. 返回:Boolean。找到返回True。
  502. '''
  503. def getBlackChannel(self, channelCount, blackThreshold=20, blackRate=2.0):
  504. result = False
  505. # 根据频道数量遍历;
  506. for i in range(0, channelCount):
  507. # 截图,取左半边;
  508. pic_path = self.takePicture()
  509. img = cv.imread(pic_path)
  510. pic_path2 = os.path.join(getSATTmpDIR(), "menutree_focus_area_half.png")
  511. self.imgCMP.saveCropPic(pic_path, pic_path2, (0, 0, img.shape[1] / 2, img.shape[0]))
  512. # 是否符合要求;
  513. result = self.imgCMP.isBlack(pic_path2, blackThreshold, 10, 1 - blackRate)
  514. if result is True:
  515. break
  516. # 下一频道号;
  517. self.redRat3.sendKey('C+')
  518. time.sleep(4)
  519. # endfor
  520. return result
  521. '''
  522. 函数:设置信源。
  523. 参数:
  524. optionName 目标信源;
  525. 返回:
  526. 注意:切换信源是特殊的情况处理:
  527. 1、信源菜单消失过快,会导致ocr识别完成后,菜单已消失。
  528. 2、usb信源下,可能会调用source按键失败,所以需要调用其他退出键(ok、exit、return)
  529. '''
  530. def setSourceValue(self, optionParent, optionName):
  531. self.info(u"【%s】" % optionName)
  532. CTMenu.sourceInput.setPattern(11)
  533. sourceList = self.__optionExcel.getOptionAllSiblingItemTextList1d(optionName)
  534. self.__curOpa = COptionAction(optionName, None, self.__optionConfig, self.__optionExcel)
  535. # 检测路径是否有效;
  536. if not self.__curOpa.checkRunOptionPath():
  537. return False
  538. # 首先,调用根菜单;
  539. self.__curOpa.callFirstOptionShortCutKey()
  540. # 遍历到目标option中;
  541. if self.__move2SourceNode(self.__curOpa, True, sourceList.__len__() * 2)[0] is False:
  542. if self.__move2SourceNode(self.__curOpa, False, sourceList.__len__() * 2)[0] is False:
  543. self.__back2Home(self.__curOpa)
  544. return False
  545. self.info(u"成功进入指定信源:%s" % optionName)
  546. return True
  547. '''
  548. 函数:识别传入的option / optionValue,是否在当前页面中存在
  549. 参数:
  550. option:在value不传入的情况下,option为非value层的option名;
  551. value:传入的情况下,option为value层的value_name,value则为value名
  552. 返回:
  553. boolean,是否识别到该option / optionValue
  554. '''
  555. def checkOptionExist(self, option, value=None):
  556. self.__curOpa = COptionAction(option, value, self.optionConfig, self.optionExcel)
  557. self.__curOpa.setCurPos(self.__curOpa.getPathLength())
  558. return self.__curOpa.isOnTargetNode()[0]
  559. '''
  560. 调用当前opa的back2ParentNode()
  561. '''
  562. def back2parentNode(self):
  563. return self.__curOpa.back2ParentNode()
  564. if __name__ == "__main__":
  565. ml = CTMenu()
  566. if 0:
  567. st = 2
  568. ml.setOptionValue('picture_preset', 'personal')
  569. time.sleep(st)
  570. ml.setOptionValue('picture_preset', 'dynamic')
  571. time.sleep(st)
  572. ml.setOptionValue('picture_preset', 'stadium')
  573. time.sleep(st)
  574. ml.setOptionValue('picture_preset', 'standard')
  575. time.sleep(st)
  576. ml.setOptionValue('picture_preset', 'natural')
  577. time.sleep(st)
  578. ml.setOptionValue('picture_preset', 'movie')
  579. ml.openOption('picture_preset')
  580. ml.setValue('movie')
  581. print "--------------------------------------------------"
  582. ml.openOption('picture_preset')
  583. ml.setValue('dynamic')
  584. print "--------------------------------------------------"
  585. ml.openOption('brightness')
  586. ml.setValue(10)
  587. ml.back2Home()
  588. if 0:
  589. st = 5
  590. value = random.randint(0, 100)
  591. time.sleep(st)
  592. ml.setOptionValue('brightness', value)
  593. time.sleep(st)
  594. ml.setOptionValue('contrast', value)
  595. time.sleep(st)
  596. ml.setOptionValue('saturation', value)
  597. time.sleep(st)
  598. ml.setOptionValue('tint', value)
  599. time.sleep(st)
  600. ml.setOptionValue('sharpness', value)
  601. time.sleep(st)
  602. ml.setOptionValue('backlight', value)
  603. if 0:
  604. st = 2
  605. ml.checkOptionValue('picture_preset', 'personal')
  606. time.sleep(st)
  607. ml.checkOptionValue('picture_preset', 'dynamic')
  608. time.sleep(st)
  609. ml.checkOptionValue('picture_preset', 'stadium')
  610. time.sleep(st)
  611. ml.checkOptionValue('picture_preset', 'standard')
  612. time.sleep(st)
  613. ml.checkOptionValue('picture_preset', 'natural')
  614. time.sleep(st)
  615. ml.checkOptionValue('picture_preset', 'movie')
  616. if 0:
  617. st = 1
  618. value = random.randint(0, 100)
  619. ml.setOptionValue('backlight', value)
  620. time.sleep(st)
  621. ml.checkOptionValue('backlight', value + 10)
  622. time.sleep(st)
  623. ml.checkOptionValue('backlight', value)
  624. time.sleep(st)
  625. ml.setOptionValue('brightness', value)
  626. time.sleep(st)
  627. ml.checkOptionValue('brightness', value + 10)
  628. time.sleep(st)
  629. ml.checkOptionValue('brightness', value)
  630. time.sleep(st)
  631. ml.setOptionValue('contrast', value)
  632. time.sleep(st)
  633. ml.checkOptionValue('contrast', value + 10)
  634. time.sleep(st)
  635. ml.checkOptionValue('contrast', value)
  636. time.sleep(st)
  637. ml.setOptionValue('saturation', value)
  638. time.sleep(st)
  639. ml.checkOptionValue('saturation', value + 10)
  640. time.sleep(st)
  641. ml.checkOptionValue('saturation', value)
  642. time.sleep(st)
  643. ml.setOptionValue('tint', value)
  644. time.sleep(st)
  645. ml.checkOptionValue('tint', value + 10)
  646. time.sleep(st)
  647. ml.checkOptionValue('tint', value)
  648. time.sleep(st)
  649. ml.setOptionValue('sharpness', value)
  650. time.sleep(st)
  651. ml.checkOptionValue('sharpness', value + 10)
  652. time.sleep(st)
  653. ml.checkOptionValue('sharpness', value)
  654. time.sleep(st)
  655. if 0:
  656. st = 30
  657. ml.openOption('picture_preset')
  658. time.sleep(st)
  659. ml.openOption('brightness')
  660. time.sleep(st)
  661. ml.openOption('contrast')
  662. time.sleep(st)
  663. ml.openOption('tint')
  664. time.sleep(st)
  665. ml.openOption('sharpness')
  666. time.sleep(st)
  667. ml.openOption('backlight')
  668. time.sleep(st)
  669. if 0:
  670. st = 30
  671. value = random.randint(0, 100)
  672. ml.focusOptionValue('brightness', value)
  673. time.sleep(st)
  674. ml.focusOptionValue('contrast', value)
  675. time.sleep(st)
  676. ml.focusOptionValue('saturation', value)
  677. time.sleep(st)
  678. ml.focusOptionValue('tint', value)
  679. time.sleep(st)
  680. ml.focusOptionValue('sharpness', value)
  681. time.sleep(st)
  682. ml.focusOptionValue('backlight', value)
  683. time.sleep(st)
  684. ml.focusOptionValue('picture_preset', 'personal')
  685. time.sleep(st)
  686. ml.focusOptionValue('picture_preset', 'dynamic')
  687. time.sleep(st)
  688. ml.focusOptionValue('picture_preset', 'stadium')
  689. time.sleep(st)
  690. ml.focusOptionValue('picture_preset', 'standard')
  691. time.sleep(st)
  692. ml.focusOptionValue('picture_preset', 'natural')
  693. time.sleep(st)
  694. ml.focusOptionValue('picture_preset', 'movie')
  695. if 0:
  696. st = 2
  697. ml.getOptionValue('brightness')
  698. time.sleep(st)
  699. ml.getOptionValue('contrast')
  700. time.sleep(st)
  701. ml.getOptionValue('saturation')
  702. time.sleep(st)
  703. ml.getOptionValue('tint')
  704. time.sleep(st)
  705. ml.getOptionValue('sharpness')
  706. time.sleep(st)
  707. ml.getOptionValue('backlight')
  708. time.sleep(st)
  709. ml.getOptionValue('picture_preset')
  710. if 0:
  711. ml.openOption('picture')
  712. ml.moveToOption('brightness')
  713. ml.moveToOption('picture_reset')
  714. ml.moveToOption('picture_preset')
  715. if 0:
  716. # ml.setSourceValue('hdmi1')
  717. ml.setSourceValue('hdmi2')
  718. # ml.setSourceValue('dtv')
  719. print u'------------------------------'
  720. ml.setSourceValue('av')
  721. if 0:
  722. # ml.setOptionValue('auto_volume_control', 'off')
  723. # ml.setOptionValue('lock', 'on')
  724. ml.setSourceValue('dtv')