IAPCardView.cpp 4.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127
  1. //
  2. // IAPCardView.cpp
  3. // demo
  4. //
  5. // Created by Red_mini on 2024/10/25.
  6. //
  7. #include "IAPCardView.hpp"
  8. void IAPCardView::setDelegate(IAPCardViewDelegate *delegate){
  9. if(delegate){
  10. _delegate = delegate;
  11. }
  12. }
  13. IAPCardView* IAPCardView::create(cocos2d::Size &viewSize, sDotCfg &dotCfg){
  14. // 创建 PageView 用于分页滑动卡片
  15. IAPCardView* ret = new IAPCardView();
  16. if (ret && ret->_init(viewSize, dotCfg)) {
  17. ret->autorelease();
  18. return ret;
  19. } else {
  20. delete ret;
  21. return nullptr;
  22. }
  23. }
  24. void IAPCardView::addCard(Node* card){
  25. if(card == nullptr) return;
  26. auto layout = ui::Layout::create();
  27. layout->setContentSize(_pageView->getContentSize());
  28. // 将卡片添加到布局并居中
  29. card->setPosition(Vec2(layout->getContentSize().width / 2, layout->getContentSize().height / 2));
  30. layout->addChild(card);
  31. // 添加到 PageView
  32. _pageView->addPage(layout);
  33. // 添加指示点
  34. float spacing = _dotCfg.sepWidth;
  35. auto newDot = Sprite::create(_dotCfg.normalSp);
  36. newDot->setPosition(Vec2(_indicators.size() * spacing, _dotCfg.yStart));
  37. _indicators.push_back(newDot);
  38. // 指示点添加到父节点中
  39. _indicatorNode->addChild(newDot);
  40. // 如果该卡片是添加的第一个
  41. if(_indicators.size() == 1){
  42. auto indicator = dynamic_cast<Sprite*>(_indicators[0]);
  43. if(indicator){
  44. indicator->setTexture(_dotCfg.hightSp); // 切换为选中图片
  45. }
  46. }
  47. // 调整指示点位置
  48. float indicatorNodeWidth = (_indicators.size() - 1) * spacing;
  49. _indicatorNode->setPosition(Vec2(_pageView->getContentSize().width / 2 - indicatorNodeWidth / 2, _dotCfg.yStart)); // 调整y轴位置
  50. }
  51. void IAPCardView::removeCard(int index){
  52. // 确保索引合法
  53. if (index < 0 || index >= _pageView->getPages().size()) {
  54. CCLOG("Invalid index: %d", index);
  55. return;
  56. }
  57. // 从 PageView 中移除指定页面
  58. _pageView->removePageAtIndex(index);
  59. // 从指示点数组中移除指定指示点,并从父节点中删除
  60. if (index < _indicators.size()) {
  61. auto indicator = _indicators[index];
  62. _indicatorNode->removeChild(indicator);
  63. _indicators.erase(_indicators.begin() + index);
  64. }
  65. // 更新剩余指示点的位置
  66. float spacing = _dotCfg.sepWidth;
  67. for (int i = 0; i < _indicators.size(); ++i) {
  68. _indicators[i]->setPosition(Vec2(i * spacing, _dotCfg.yStart));
  69. }
  70. }
  71. bool IAPCardView::_init(Size &viewSize, sDotCfg &dotCfg){
  72. _viewSize = viewSize;
  73. _dotCfg = dotCfg;
  74. // 创建 PageView 用于分页滑动卡片
  75. _pageView = ui::PageView::create();
  76. _pageView->setContentSize(viewSize);
  77. // 创建总指示器Node
  78. _indicatorNode = Node::create();
  79. // 设置 PageView 的分页切换效果(滑动自动切换)
  80. _pageView->setUsingCustomScrollThreshold(true); // 启用自定义滑动阈值
  81. _pageView->setCustomScrollThreshold(50); // 设置触发翻页的滑动距离阈值
  82. _pageView->setAutoScrollStopEpsilon(0.05f); // 提高自动滚动停止的精度
  83. this->addChild(_pageView);
  84. this->addChild(_indicatorNode);
  85. // 添加回调函数监听pageView变化
  86. _pageView->addEventListener([&](Ref* sender, ui::PageView::EventType type) {
  87. auto pageView = dynamic_cast<ui::PageView*>(sender);
  88. int currentPageIndex = pageView->getCurrentPageIndex();
  89. // 更新指示点的图片,当前页的指示点变为选中状态,其他保持未选中
  90. for (int i = 0; i < _indicators.size(); i++) {
  91. auto indicator = dynamic_cast<Sprite*>(_indicators[i]);
  92. if (i == currentPageIndex) {
  93. indicator->setTexture(_dotCfg.hightSp); // 切换为选中图片
  94. } else {
  95. indicator->setTexture(_dotCfg.normalSp); // 切换为未选中图片
  96. }
  97. }
  98. // 如果delegate存在通知delegate卡片页数改变
  99. if(_delegate){
  100. _delegate->onCardChanged(currentPageIndex);
  101. }
  102. });
  103. return true;
  104. }