GoodsItem.lua 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517
  1. local CacheWidget = requireUtil("CacheWidget")
  2. local GoodsItem = class("GoodsItem", CacheWidget)
  3. local ItemConfigProxy = global.Facade:retrieveProxy(global.ProxyTable.ItemConfigProxy)
  4. local RichTextHelp = requireUtil("RichTextHelp")
  5. -- 点击事件
  6. local kTouchAll = 0
  7. local kTouchPress = 1 -- 长按
  8. local kTouchClick = 2 -- 点击
  9. local kTouchWidget = 3 -- widget touch
  10. local kDoubleTime = global.MMO.CLICK_DOUBLE_TIME
  11. local itemMoveState = {
  12. begin = 1,
  13. moving = 2,
  14. end_move = 3,
  15. }
  16. local mmax = math.max
  17. local mmin = math.min
  18. local sformat = string.format
  19. function GoodsItem:ctor()
  20. GoodsItem.super.ctor(self)
  21. self._pressCallback = nil
  22. self._clickCallback = nil
  23. self._replaceClickEvent = nil
  24. self._iconTouchEventListener = nil
  25. self._doubleEvent = nil
  26. self._lastClickTime = nil
  27. self._clickDelayHandler = nil
  28. self._moveCancelCallBack = nil
  29. self._data = nil
  30. self._itemData = nil
  31. self._from = nil
  32. self._movable = nil
  33. self._canLooks = nil
  34. self._mouseEventCheckTimes = nil
  35. self._moveItem = nil
  36. self._noSwallow = nil
  37. self._extraLockStatus = nil
  38. self._greyStatus = nil
  39. self._itemTipsCenter = nil
  40. end
  41. function GoodsItem:init(data)
  42. self._quickUI = ui_delegate(self)
  43. self:InitGUI(data)
  44. end
  45. function GoodsItem:InitGUI(data)
  46. self._itemClass = require(SLDefine.LUAFile.LUA_FILE_ITEM).new(self, data)
  47. self:Cleanup()
  48. self:InitData(data)
  49. end
  50. function GoodsItem:InitData(data)
  51. if tonumber(data) then
  52. local index = data
  53. data = {}
  54. data.index = index
  55. end
  56. local ItemConfigProxy = global.Facade:retrieveProxy(global.ProxyTable.ItemConfigProxy)
  57. data = data or {}
  58. self._data = data
  59. self._itemData = data.itemData or ItemConfigProxy:GetItemDataByIndex(data.index)
  60. self._mouseEventCheckTimes = data.mouseCheckTimes
  61. self._moveItem = data.moveItem
  62. if data.from then
  63. self._from = data.from
  64. end
  65. -- 是否注册鼠标tips
  66. local isShowMouseTip = data.noMouseTips
  67. if not isShowMouseTip and global.isWinPlayMode then
  68. self:RegisterWin32MouseMove()
  69. global.mouseEventController:registerMouseButtonEvent(self, {checkIsVisible = true})
  70. end
  71. local noSwallow = data.noSwallow
  72. if type(noSwallow) == "boolean" then
  73. self:setItemTouchSwallow(noSwallow)
  74. end
  75. -- 是否查看道具信息
  76. local look = data.look
  77. -- 是否可移动
  78. local movable = data.movable
  79. if look or movable then
  80. self._movable = movable
  81. self._canLooks = look
  82. self:addLookItemInfoEvent(data.posType)
  83. end
  84. end
  85. function GoodsItem:OnEnter()
  86. end
  87. function GoodsItem:OnExit()
  88. if self._clickDelayHandler then
  89. UnSchedule(self._clickDelayHandler)
  90. self._clickDelayHandler = nil
  91. end
  92. if not global.isWinPlayMode then
  93. if not self._moveItem and self._itemData and self._itemData.MakeIndex then
  94. global.Facade:sendNotification(global.NoticeTable.Layer_Moved_Cancel, {MakeIndex = self._itemData.MakeIndex})
  95. end
  96. end
  97. local eventDispatcher = cc.Director:getInstance():getEventDispatcher()
  98. eventDispatcher:removeEventListenersForTarget(self, true)
  99. end
  100. function GoodsItem:Cleanup()
  101. self._movingState = false
  102. self._data = nil
  103. self._itemData = nil
  104. self._from = nil
  105. self._movable = nil
  106. self._canLooks = nil
  107. self._mouseEventCheckTimes = nil
  108. self._moveItem = nil
  109. self._noSwallow = nil
  110. self._extraLockStatus = nil
  111. self._greyStatus = nil
  112. self._pressCallback = nil
  113. self._clickCallback = nil
  114. self._replaceClickEvent = nil
  115. self._iconTouchEventListener = nil
  116. self._doubleEvent = nil
  117. self._lastClickTime = nil
  118. self._clickDelayHandler = nil
  119. self._moveCancelCallBack = nil
  120. end
  121. function GoodsItem:OnRunFunc(func, ...)
  122. if self._itemClass and self._itemClass[func] and type(self._itemClass[func]) == "function" then
  123. return self._itemClass[func](self._itemClass, ...)
  124. end
  125. end
  126. function GoodsItem:UpdateItem(data)
  127. self._itemClass:Cleanup()
  128. self._itemClass:InitData(data)
  129. self:Cleanup()
  130. self:InitData(data)
  131. end
  132. function GoodsItem:setCount(count)
  133. self._itemClass:SetCount(count)
  134. end
  135. function GoodsItem:setItemExtraLockStatus(status)
  136. self._extraLockStatus = status
  137. self._itemClass:SetItemExtraLockStatus(status)
  138. end
  139. function GoodsItem:setIconGrey(value)
  140. self._greyStatus = value
  141. self._itemClass:SetIconGrey(value)
  142. end
  143. function GoodsItem:setItemPowerTag()
  144. self._itemClass:SetItemPowerFlag()
  145. end
  146. function GoodsItem:UpdateGoodsItem(itemData)
  147. self._itemData = itemData
  148. self._itemClass:UpdateGoodsItem(itemData)
  149. end
  150. function GoodsItem:SetItemIndex(index)
  151. self._itemData = ItemConfigProxy:GetItemDataByIndex(index)
  152. if self._itemData.Looks == null then return end
  153. self._itemClass._looks = self._itemData.Looks
  154. self._itemClass._index = index
  155. self._itemClass:SetItemIndex(index)
  156. GUI:setVisible(self._itemClass._ui["Button_icon"], true)
  157. end
  158. function GoodsItem:setItemTouchSwallow(bool)
  159. if not type(bool) == "boolean" then
  160. return false
  161. end
  162. self._noSwallow = not bool
  163. self._itemClass:SetItemTouchSwallow(bool)
  164. end
  165. function GoodsItem:SetMoveEable(enable)
  166. self._movable = enable
  167. end
  168. function GoodsItem:GetLayoutExtra()
  169. return self._quickUI.Panel_extra
  170. end
  171. function GoodsItem:GetButtonIcon()
  172. return self._quickUI.Button_icon
  173. end
  174. function GoodsItem:GetTextCount()
  175. return self._quickUI.Text_count
  176. end
  177. function GoodsItem:SetGoodItemState( state, pos )
  178. if not self._from or not self._movable then
  179. return
  180. end
  181. if itemMoveState.begin == state then
  182. self:setVisible(false)
  183. self._movingState = true
  184. global.Facade:sendNotification(global.NoticeTable.Layer_ItemTips_Close)
  185. global.Facade:sendNotification(global.NoticeTable.Layer_Moved_Begin,{
  186. pos = pos,
  187. itemData = self._itemData,
  188. cancelCallBack = self._moveCancelCallBack,
  189. goodsItem = self,
  190. from = self._from
  191. })
  192. elseif itemMoveState.moving == state then
  193. elseif itemMoveState.end_move == state then
  194. global.Facade:sendNotification(global.NoticeTable.Layer_Moved_End, pos)
  195. end
  196. end
  197. function GoodsItem:resetMoveState(bool)
  198. self._movingState = bool
  199. self:setVisible(not bool)
  200. end
  201. function GoodsItem:showIteminfo(posType, setPos)
  202. if not self._itemData or self._movingState then
  203. return nil
  204. end
  205. local result = true
  206. if self._replaceClickEvent then
  207. result = self._replaceClickEvent(self)
  208. end
  209. if result then
  210. local pos = self:getWorldPosition()
  211. -- pick item audio
  212. if global.isWinPlayMode and self._movable then
  213. if setPos and next(setPos) then-- 交换道具位置后的
  214. pos = setPos
  215. end
  216. self:SetGoodItemState(itemMoveState.begin, pos)
  217. else
  218. if self._canLooks and not global.isWinPlayMode then
  219. if not self._itemData or next(self._itemData) == nil then
  220. return
  221. end
  222. local data = {}
  223. data.itemData = self._itemData
  224. data.pos = pos
  225. data.from = self._from
  226. data.lookPlayer = self._data and self._data.lookPlayer
  227. global.Facade:sendNotification(global.NoticeTable.Layer_ItemTips_Open, data)
  228. end
  229. end
  230. end
  231. end
  232. function GoodsItem:addLookItemInfoEvent(posType, eventType)
  233. eventType = eventType or kTouchClick
  234. self:addTouchEventListener(function()
  235. self:showIteminfo(posType)
  236. end, eventType)
  237. end
  238. function GoodsItem:addReplaceClickEventListener(callback)
  239. self._replaceClickEvent = callback
  240. end
  241. function GoodsItem:addDoubleEventListener(callback)
  242. self._doubleEvent = callback
  243. end
  244. function GoodsItem:addMoveCancelCallBack(callback)
  245. self._moveCancelCallBack = callback
  246. end
  247. function GoodsItem:addPressCallBack(callback)
  248. self._pressCallback = callback
  249. end
  250. function GoodsItem:SetChooseState(visible)
  251. self._quickUI.Image_choosTag:setVisible(visible)
  252. end
  253. -- 注册鼠标移动事件
  254. function GoodsItem:RegisterWin32MouseMove()
  255. local function UnScheduler()
  256. if self._delayFunc then
  257. cc.Director:getInstance():getScheduler():unscheduleScriptEntry(self._delayFunc)
  258. self._delayFunc = nil
  259. end
  260. end
  261. local function onShowItemTips(touchPos)
  262. if self._movingState then
  263. return false
  264. end
  265. if not (self._itemData and next(self._itemData)) then
  266. return false
  267. end
  268. if not CheckNodeCanCallBack(self, touchPos, self._mouseEventCheckTimes) then
  269. return false
  270. end
  271. local data = {}
  272. data.itemData = self._itemData
  273. data.pos = self:getWorldPosition()
  274. data.from = self._from
  275. data.lookPlayer = self._data and self._data.lookPlayer
  276. SL:OpenItemTips(data)
  277. end
  278. local function onLeaveFunc()
  279. SL:CloseItemTips()
  280. UnScheduler()
  281. end
  282. local function onEnterFunc(touchPos)
  283. if self._delayFunc then
  284. return false
  285. end
  286. self._delayFunc = PerformWithDelayGlobal(function()
  287. onShowItemTips(touchPos)
  288. end, global.MMO.PC_TIPS_DELAY_TIME)
  289. end
  290. GUI:addMouseMoveEvent(self, {onEnterFunc = onEnterFunc, onLeaveFunc = onLeaveFunc, checkIsVisible = true})
  291. self.isSignMouListner = true
  292. end
  293. --注册鼠标滚动回调
  294. function GoodsItem:RegisterWin32MouseMoveScrollCall(data)
  295. global.Facade:sendNotification(global.NoticeTable.Layer_ItemTips_Mouse_Scroll, data)
  296. end
  297. function GoodsItem:addTouchEventListener(callback, eventType)
  298. -- 0:长按,点击 1:长按 2:点击 3:touch响应回调
  299. eventType = eventType or kTouchClick
  300. if eventType == kTouchAll then
  301. self._pressCallback = callback
  302. self._clickCallback = callback
  303. elseif eventType == kTouchPress then
  304. self._pressCallback = callback
  305. elseif eventType == kTouchClick then
  306. self._clickCallback = callback
  307. elseif eventType == kTouchWidget then
  308. self._iconTouchEventListener = callback
  309. end
  310. local isEventPress = false
  311. local isMoved = true
  312. local canCallBack = true
  313. local isMobile = not global.isWinPlayMode
  314. local isMoveNode = false
  315. local function delayCallback()
  316. isEventPress = true
  317. if self._pressCallback then
  318. if not self._pressCallback then
  319. return false
  320. end
  321. if not isMoved then
  322. self._pressCallback(self)
  323. return false
  324. end
  325. local movedPos = self._quickUI.Panel_bg:getTouchMovePosition()
  326. local beganPos = self._quickUI.Panel_bg:getTouchBeganPosition()
  327. local diff = cc.pSub(movedPos, beganPos)
  328. local distSq = cc.pLengthSQ(diff)
  329. if distSq <= 100 then
  330. self._pressCallback(self)
  331. end
  332. end
  333. end
  334. local function touchEvent(_, eventType)
  335. if not isMobile then
  336. local ItemMoveProxy = global.Facade:retrieveProxy(global.ProxyTable.ItemMoveProxy)
  337. local itemMoving = ItemMoveProxy:GetMovingItemState()
  338. if itemMoving then --在道具移动中
  339. if eventType == 0 then
  340. self:retain()
  341. canCallBack = ItemMoveProxy:GetItemMoveFrome() ~= ItemMoveProxy.ItemGoTo.BAG or self._from ~= ItemMoveProxy.ItemGoTo.BAG
  342. end
  343. return
  344. end
  345. local BagProxy = global.Facade:retrieveProxy(global.ProxyTable.Bag)
  346. if BagProxy:GetBagCollimator() then
  347. self:retain()
  348. return
  349. end
  350. end
  351. if self._iconTouchEventListener then
  352. self._iconTouchEventListener(self, eventType)
  353. end
  354. if eventType == 0 then
  355. self:retain()
  356. isEventPress = false
  357. isMoved = false
  358. canCallBack = true
  359. isMoveNode = false
  360. if self._pressCallback then
  361. self._quickUI.Panel_bg:stopAllActions()
  362. performWithDelay(self._quickUI.Panel_bg, delayCallback, kDoubleTime)
  363. end
  364. elseif eventType == 1 then
  365. local movedPos = self._quickUI.Panel_bg:getTouchMovePosition()
  366. local beganPos = self._quickUI.Panel_bg:getTouchBeganPosition()
  367. local diff = cc.pSub(movedPos, beganPos)
  368. local distSq = cc.pLengthSQ(diff)
  369. if not isMoved and distSq > 100 then
  370. isMoved = true
  371. if isMobile and self._movable then
  372. local beginMovePos = self:getWorldPosition()
  373. self:SetGoodItemState(itemMoveState.begin, beginMovePos)
  374. end
  375. end
  376. if isMobile and self._movable then
  377. local movedPos = self._quickUI.Panel_bg:getTouchMovePosition()
  378. global.Facade:sendNotification(global.NoticeTable.Layer_Moved_Moving,{pos = movedPos})
  379. end
  380. elseif eventType == 2 or eventType == 3 then
  381. self:autorelease()
  382. self._quickUI.Panel_bg:stopAllActions()
  383. if not isMoved then
  384. if not isEventPress then
  385. -- 判断是否有双击事件
  386. if self._doubleEvent then
  387. -- 记录上一次点击时间
  388. if not self._lastClickTime then
  389. self._lastClickTime = true
  390. -- 记录单击触发
  391. self._clickDelayHandler =
  392. PerformWithDelayGlobal(
  393. function()
  394. if self._clickCallback and canCallBack then
  395. self._clickCallback(self, eventType)
  396. canCallBack = false
  397. end
  398. self._lastClickTime = nil
  399. end,
  400. kDoubleTime
  401. )
  402. else
  403. if self._clickDelayHandler then
  404. UnSchedule(self._clickDelayHandler)
  405. self._clickDelayHandler = nil
  406. end
  407. if self._doubleEvent then
  408. self._doubleEvent(self)
  409. end
  410. self._lastClickTime = nil
  411. end
  412. else
  413. if self._clickCallback and canCallBack then
  414. self._clickCallback(self, eventType)
  415. canCallBack = false
  416. end
  417. end
  418. end
  419. else
  420. if isMobile and self._movable then
  421. local endPos = self._quickUI.Panel_bg:getTouchEndPosition()
  422. self:SetGoodItemState(itemMoveState.end_move, endPos)
  423. end
  424. end
  425. end
  426. end
  427. RemoveAllWidgetTouchEventListener(self._quickUI.Panel_bg)
  428. self._quickUI.Panel_bg:addTouchEventListener(touchEvent)
  429. self._quickUI.Panel_bg:setTouchEnabled(true)
  430. self._quickUI.Panel_bg:setSwallowTouches(not self._noSwallow)
  431. end
  432. function GoodsItem:DelayTouchEnabled(delay)
  433. GUI:delayTouchEnabled(self._quickUI.Panel_bg, delay)
  434. end
  435. return GoodsItem