#include "RUTableView.h" NS_RU_BEGIN RUTableView* RUTableView::create(cocos2d::extension::TableViewDataSourceSmooth* dataSource, cocos2d::Size size) { return RUTableView::create(dataSource, size, nullptr); } RUTableView* RUTableView::create(cocos2d::extension::TableViewDataSourceSmooth *dataSource, cocos2d::Size size, cocos2d::Node *container) { RUTableView *table_view = new (std::nothrow) RUTableView(); table_view->initWithViewSize(size, container); table_view->autorelease(); table_view->setDataSource(dataSource); ///yjz_add RUTableDataModel* m = dynamic_cast(dataSource) ; if(m) { bool opacity = m->cascadeOpacity() ; table_view->setCascadeOpacityEnabled(opacity) ; table_view->_container->setCascadeOpacityEnabled(opacity) ; } /// table_view->_updateCellPositions(); table_view->_updateContentSize(); return table_view; } void RUTableView::reloadData(bool cleanUp) { _oldDirection = Direction::NONE; for(const auto &cell : _cellsUsed) { if(_tableViewDelegate != nullptr) { _tableViewDelegate->tableCellWillRecycle(this, cell); } _cellsFreed.pushBack(cell); cell->reset(); if (cell->getParent() == this->getContainer()) { this->getContainer()->removeChild(cell, cleanUp); } } _indices->clear(); _cellsUsed.clear(); this->_updateCellPositions(); this->_updateContentSize(); if (_dataSource->numberOfCellsInTableView(this) > 0) { this->scrollViewDidScroll(this); } } void RUTableView::setVerticalFillOrder(VerticalFillOrder fillOrder,bool cleanUp) { if (_vordering != fillOrder) { _vordering = fillOrder; if (!_cellsUsed.empty()) { this->reloadData(cleanUp); } } } void RUTableView::safeSetContentOffset(Vec2 offset) { // if(_bounceable && checkIsCanMove(offset))return; if(_bounceable) return; if (!_bounceable) { const Vec2 minOffset = this->minContainerOffset(); const Vec2 maxOffset = this->maxContainerOffset(); offset.x = MAX(minOffset.x, MIN(maxOffset.x, offset.x)); offset.y = MAX(minOffset.y, MIN(maxOffset.y, offset.y)); } _container->setPosition(offset); safeScrollViewDidScroll() ; } void RUTableView::safeScrollViewDidScroll() { long countOfItems = _dataSource->numberOfCellsInTableView(this); if (0 == countOfItems) { return; } if (_isUsedCellsDirty) { _isUsedCellsDirty = false; std::sort(_cellsUsed.begin(), _cellsUsed.end(), [](TableViewCell *a, TableViewCell *b) -> bool{ return a->getIdx() < b->getIdx(); }); } ssize_t startIdx = 0, endIdx = 0, idx = 0, maxIdx = 0; Vec2 offset = this->getContentOffset() * -1; maxIdx = MAX(countOfItems-1, 0); if (_vordering == VerticalFillOrder::TOP_DOWN) { offset.y = offset.y + _viewSize.height/this->getContainer()->getScaleY(); } startIdx = this->_indexFromOffset(offset); if (startIdx == CC_INVALID_INDEX) { startIdx = countOfItems - 1; } if (_vordering == VerticalFillOrder::TOP_DOWN) { offset.y -= _viewSize.height/this->getContainer()->getScaleY(); } else { offset.y += _viewSize.height/this->getContainer()->getScaleY(); } offset.x += _viewSize.width/this->getContainer()->getScaleX(); endIdx = this->_indexFromOffset(offset); if (endIdx == CC_INVALID_INDEX) { endIdx = countOfItems - 1; } if (!_cellsUsed.empty()) { auto cell = _cellsUsed.at(0); idx = cell->getIdx(); while(idx < startIdx) { this->_moveCellOutOfSight(cell); if (!_cellsUsed.empty()) { cell = _cellsUsed.at(0); idx = cell->getIdx(); } else { break; } } } if (!_cellsUsed.empty()) { auto cell = _cellsUsed.back(); idx = cell->getIdx(); while(idx <= maxIdx && idx > endIdx) { this->_moveCellOutOfSight(cell); if (!_cellsUsed.empty()) { cell = _cellsUsed.back(); idx = cell->getIdx(); } else { break; } } } for (long i = startIdx; i <= endIdx; i++) { if (_indices->find(i) != _indices->end()) { continue; } this->updateCellAtIndex(i); } ///注释了ScrollViewDidScroll的此处 // if(_tableViewDelegate != nullptr) { // _tableViewDelegate->scrollViewDidScroll(this); // } } int RUTableView::getVisibleCellIndex() { cocos2d::Rect viewRect = this->getViewRect(); cocos2d::Vec2 point = getContainer() ->convertToNodeSpace(cocos2d::Vec2(viewRect.getMidX(),viewRect.getMidY())) ; int index = (int)this->_indexFromOffset(point); if(index<0) { int maxIndex = (int)_dataSource->numberOfCellsInTableView(this)-1; index = maxIndex ; } return index ; } Size RUTableView::tableSize() { return getContainer()->getContentSize() ; } Size RUTableView::maxCellSize() { return _dataSource->cellSizeForTable(this) ; } #pragma mark - 吸附 void RUTableView::setAbsorb(bool absorb,bool bounced, bool bFixedIndex) { _absorb = absorb ; _absordBounced = bounced ; _fixedIndex4Absorb = bFixedIndex; if(_absorb) { scheduleUpdate() ; } else { unscheduleUpdate() ; } }; int RUTableView::recycleIndex() { if(_recycle) { int total = (int)_dataSource->numberOfCellsInTableView(this) ; if(total%2==1) { //循环时,cell个数必须是偶数 assert(0) ; } return total/ 2 - 1 ; } else { return INT_MIN ; } }; Vec2 RUTableView::localDistanceToPercentViewSize(Vec2 worldPos,float percentX,float percentY) { Vec2 posInView(_viewSize.width*percentX/100,_viewSize.height*percentY/100) ; Vec2 worldPosInView ; worldPosInView = convertToWorldSpace(posInView) ; Vec2 viewPosInContainer ; Vec2 userPosInContaner ; AffineTransform toContainerSpace = _container->getWorldToNodeAffineTransform() ; viewPosInContainer = __CCPointApplyAffineTransform(viewPosInContainer, toContainerSpace) ; userPosInContaner = __CCPointApplyAffineTransform(worldPos,toContainerSpace) ; Vec2 distance = viewPosInContainer - userPosInContaner ; return distance ; } Vec2 RUTableView::offsetFromIndex(ssize_t cellIndex) { return _offsetFromIndex(cellIndex) ; } void RUTableView::setRecycle(bool recycle) { _recycle = recycle ; } #pragma mark - 自制 void RUTableView::updateCellAtIndex(int cellIndex) { if (_indices->find(cellIndex) == _indices->end()) { this->TableViewSmooth::updateCellAtIndex(cellIndex); } } float RUTableView::scrollToNodeInView(int cellIndex,Vec2 posInCell,Vec2 percentInView,float duration) { if (_indices->find(cellIndex) == _indices->end()) { this->updateCellAtIndex(cellIndex); } float percentXInView = percentInView.x ; float percentYInView = percentInView.y ; Size viewSize = getViewSize() ; Vec2 posInView(viewSize.width*percentXInView/100,viewSize.height*percentYInView/100); Vec2 cellFloorOffset = _offsetFromIndex(cellIndex) ; //已包含对BOTTOM_UP和TOP_DOWN的判断 Vec2 nodePos = cellFloorOffset + posInCell ; Vec2 offset ; if(_direction == cocos2d::extension::ScrollViewSmooth::Direction::VERTICAL) { float offsetY = nodePos.y - posInView.y ; offset.set(0, -offsetY) ; } setContentOffsetInDuration(offset,duration) ; return duration ; } float RUTableView::scrollToNodeInView(int cellIndex,Node* node,Vec2 percentInView,float duration,bool strict) { if (_indices->find(cellIndex) == _indices->end()) { this->updateCellAtIndex(cellIndex); } float percentXInView = percentInView.x ; float percentYInView = percentInView.y ; Size viewSize = getViewSize() ; Vec2 posInView(viewSize.width*percentXInView/100,viewSize.height*percentYInView/100); Vec2 worldPos = node->convertToWorldSpaceAR(Vec2::ZERO) ; Vec2 nodePos = getContainer()->convertToNodeSpaceAR(worldPos) ; Vec2 offset ; if(_direction == cocos2d::extension::ScrollViewSmooth::Direction::VERTICAL) { float offsetY = nodePos.y - posInView.y ; offset.set(0, -offsetY) ; } if(durationminContainerOffset(); const Vec2 maxOffset = this->maxContainerOffset(); offset.x = MAX(minOffset.x, MIN(maxOffset.x, offset.x)); offset.y = MAX(minOffset.y, MIN(maxOffset.y, offset.y)); } safeSetContentOffset(offset) ; } else { setContentOffsetInDuration(offset,duration) ; } return duration ; } bool RUTableView::scrollToPosInView(int index,Vec2 percentInCell,Vec2 percentInView,float duration,bool bounced) { stopDeaccelerateScrolling() ; float percentXInCell = percentInCell.x ; float percentYInCell = percentInCell.y ; float percentXInView = percentInView.x ; float percentYInView = percentInView.y ; Vec2 cellFloorOffset = _offsetFromIndex(index) ; //已包含对BOTTOM_UP和TOP_DOWN的判断 auto cellSize = _dataSource->tableCellSizeForIndex(this, index) ; Vec2 posInCell(cellSize.width*percentXInCell/100,cellSize.height*percentYInCell/100) ; Vec2 posInContainer = cellFloorOffset + posInCell ; Vec2 posInViewSize(_viewSize.width*percentXInView/100,_viewSize.height*percentYInView/100); Vec2 offset ; if(_direction == cocos2d::extension::ScrollViewSmooth::Direction::VERTICAL) { float offsetY = posInContainer.y - posInViewSize.y ; offset.set(0, -offsetY) ; } Vec2 contentOffset = getContentOffset() ; if(std::fabs(contentOffset.y - offset.y)setDelegate(_tableViewDelegate); fork->setDirection(_direction) ; fork->TableViewSmooth::setVerticalFillOrder(_vordering); fork->setBounceable(false); fork->setAbsorb(false); Vec2 offset ; if(_direction == cocos2d::extension::ScrollViewSmooth::Direction::VERTICAL) { } if(_vordering == cocos2d::extension::TableViewSmooth::VerticalFillOrder::BOTTOM_UP) { offset = maxContainerOffset() ; } fork->setContentOffset(offset); // fork->setSwallowTouches(false) ; return fork ; } bool RUTableView::scrollToCellIndex(int index,float duration,bool bounced) { bool toScroll = scrollToPosInView(index, Vec2(50,100), Vec2(100,100), duration, bounced) ; return toScroll ; } void RUTableView::recycleScrollTo(int index) { if(_recycle ) { _recycleScrollIndex = index % (recycleIndex()+1) ; } } void RUTableView::recycleScrollToInDuration(int index,float duration,bool bounced) { int targetCellIndex = index; int visualIndex = getVisibleCellIndex() ; if(targetCellIndex == visualIndex) return ; if(visualIndex > recycleIndex()) { targetCellIndex += recycleIndex()+1 ; } bool toScroll = scrollToCellIndex(targetCellIndex,duration, bounced) ; if(toScroll) { scheduleOnce([this](float) { _recycleScrollIndex = INT_MIN ; }, duration, "recycleScroll") ; } } void RUTableView::recycleScrollTo(int index,float perCellDuration,bool bounced) { float duration ; { int targetCellIndex = index; int visualIndex = getVisibleCellIndex() ; if(targetCellIndex == visualIndex) return ; if(visualIndex > recycleIndex()) { targetCellIndex += recycleIndex()+1 ; } int delta = std::abs(visualIndex-targetCellIndex); duration = delta * perCellDuration ; } recycleScrollToInDuration(index,duration,bounced) ; } #pragma mark - Proteced bool RUTableView::onTouchBegan(Touch *pTouch, Event *pEvent) { if (!_bScrollable) { return false; } if (TableViewSmooth::onTouchBegan(pTouch, pEvent)) { if (_cbWhileTouchedBegin) { _cbWhileTouchedBegin(); } return true; } return false; } void RUTableView::onTouchMoved(Touch *pTouch, Event *pEvent) { TableViewSmooth::onTouchMoved(pTouch, pEvent) ; if (_cbWhileTouchedMoved) { _cbWhileTouchedMoved(_animatedScrollAction && !_animatedScrollAction->isDone()); } } void RUTableView::onTouchEnded(Touch *pTouch, Event *pEvent) { TableViewSmooth::onTouchEnded(pTouch, pEvent) ; if (_cbWhileTouchedEnd) { _cbWhileTouchedEnd(_autoScrolling); } } void RUTableView::onTouchCancelled(Touch *pTouch, Event *pEvent) { TableViewSmooth::onTouchCancelled(pTouch, pEvent) ; if (_cbWhileTouchedEnd) { _cbWhileTouchedEnd(_autoScrolling); } } void RUTableView::absorbCell(bool byAni) { int visualIndex = _fixedIndex4Absorb == -1 ? getVisibleCellIndex() : _fixedIndex4Absorb; float distanceThreshold = .0f ; bool scroll = false ; if(_direction == cocos2d::extension::ScrollViewSmooth::Direction::VERTICAL) { distanceThreshold = _dataSource->tableCellSizeForIndex(this, visualIndex).height*_AbsorbDistanceFactor ; bool b1 = scrollDistanceFbs().y INT_MIN && _absorb && _recycleScrollIndex <= recycleIndex()) { if(!isAbsorbAniRun() && !isDraging() && !isRecycleScrollAniRun()) { recycleScrollToInDuration(_recycleScrollIndex,_RecycleScrollDuration , true) ; } } ScrollViewSmooth::update(dt); } void RUTableView::setContentOffsetInDurationByBounce(Vec2 offset, float dt,float bounceDuration) { FiniteTimeAction *scroll, *expire; if (_animatedScrollAction) { stopAnimatedContentOffset(); } scroll = MoveTo::create(dt, offset); EaseElasticOut* outBounce = EaseElasticOut::create(dynamic_cast(scroll),bounceDuration) ; expire = CallFuncN::create(CC_CALLBACK_1(RUTableView::stoppedAnimatedScroll,this)); _animatedScrollAction = _container->runAction(Sequence::create(outBounce, expire, nullptr)); _animatedScrollAction->retain(); this->schedule(CC_SCHEDULE_SELECTOR(RUTableView::performedAnimatedScroll)); } void RUTableView::stopDeaccelerateScrolling() { scrollDistance(Vec2::ZERO) ; } RUTableView::~RUTableView() { //yjz_fix,model处 // class model* model = dynamic_cast(_dataSource) ; // if(model) // { // model->clear() ; // } } #pragma mark - 开放TableView/ScorllView变量的访问 Action* RUTableView::animatedScrollAction() { return _animatedScrollAction ; } Vec2 RUTableView::scrollDistanceFbs() { return Vec2(std::fabs(_scrollDistance.x),std::fabs(_scrollDistance.y)); ; } void RUTableView::scrollDistance(Vec2 customDistance) { _scrollDistance = customDistance ; } bool RUTableView::isDraging() { return _dragging ; } bool RUTableView::isScrolling() { if(_animatedScrollAction) { if (!_animatedScrollAction->isDone()) { return true; } } return _autoScrolling; } Vector RUTableView::getUsedCell() { return _cellsUsed ; } Vector RUTableView::getFreeCell() { return _cellsFreed ; } #pragma mark - TableModel RUTableDataModel::~RUTableDataModel() { clear() ; } void RUTableDataModel::clear() { for(auto iter : _cellMap) { iter.second->release() ; } _cellMap.clear() ; } Node* RUTableDataModel::getCell(int index) { if(_cellMap.find(index) == _cellMap.end()) return NULL; return _cellMap[index] ; } void RUTableDataModel::insertCell(int index,Node* cell) { if(_cellMap.find(index) != _cellMap.end()) { _cellMap[index]->release() ; _cellMap.erase(index) ; } _cellMap[index] = cell ; cell->retain() ; } void RUTableDataModel::setCascadeOpacity(bool cascadeOpacity) { _cascadeOpacity = cascadeOpacity; } bool RUTableDataModel::cascadeOpacity() { return _cascadeOpacity ; } void RUTableDataModel::scrollViewDidScroll(ScrollViewSmooth* scrollView) { RUTableView* view = dynamic_cast(scrollView) ; RUTableDataModel* model = dynamic_cast(view->getDataSource()) ; if(view && model) { if(view->recycleIndex() != INT_MIN) { if(view->getDirection() == cocos2d::extension::ScrollViewSmooth::Direction::VERTICAL) { Size viewSize = view->getViewSize() ; Vec2 minContainerOffset = view->minContainerOffset() ; Vec2 maxContainerOffset = view->maxContainerOffset() ; Vec2 contentOffset = view->getContentOffset() ; float cellHeight = model->tableCellSizeForIndex(view, view->recycleIndex()).height ; Vec2 boardCellFloorOffset = view->offsetFromIndex(view->recycleIndex()) ; //cell上边界偏移 Vec2 cellCeilOffset = boardCellFloorOffset + Vec2(0, cellHeight) ; //cell与ViewSize顶对齐时,container的偏移 Vec2 cellAlignViewCeilOffset(cellCeilOffset.x,cellCeilOffset.y - viewSize.height ); if(contentOffset.y >= maxContainerOffset.y ) { float deltaY = contentOffset.y - maxContainerOffset.y ; cellCeilOffset.y -= deltaY ; view->safeSetContentOffset(-cellCeilOffset) ; } if(contentOffset.y <= minContainerOffset.y) { float deltaY = contentOffset.y - minContainerOffset.y ; cellAlignViewCeilOffset.y+=deltaY ; view->safeSetContentOffset(-cellAlignViewCeilOffset) ; } } } } if(_scrollViewDidScroll) { _scrollViewDidScroll(scrollView) ; } // CCLOG("tableCellAtIndex %f,%f",scrollView->getContentOffset().x,scrollView->getContentOffset().y); } #pragma mark - TableViewDataSource Size RUTableDataModel::cellSizeForTable(TableViewSmooth* table) { if(_cellSizeForTable) return _cellSizeForTable(table) ; return Size() ; } ssize_t RUTableDataModel::numberOfCellsInTableView(TableViewSmooth *table) { if(_numberOfCellsInTableView) return _numberOfCellsInTableView(table) ; else { return _cellMap.size() ; } return 0 ; } Size RUTableDataModel::tableCellSizeForIndex(TableViewSmooth* table, ssize_t idx) { if(_tableCellSizeForIndex) return _tableCellSizeForIndex(table,idx) ; return Size() ; } TableViewCell* RUTableDataModel::tableCellAtIndex(TableViewSmooth *table, ssize_t idx) { if(_tableCellAtIndex) return _tableCellAtIndex(table,idx) ; else { // CCLOG("tableCellAtIndex:%d",(int)idx) ; TableViewCell *cell = table->dequeueCell(); if (cell == nullptr) { cell = new (std::nothrow) TableViewCell(); cell -> autorelease() ; } else { cell->removeAllChildrenWithCleanup(false) ; } auto iter = _cellMap.find((int)idx) ; if(iter != _cellMap.end()) { Node*& cellLayer = iter->second ; cellLayer->removeFromParentAndCleanup(false); cell->addChild(cellLayer) ; cell->setLocalZOrder(cellLayer->getLocalZOrder()) ; } cell->setCascadeOpacityEnabled(_cascadeOpacity) ; return cell ; } return NULL; } #pragma mark - TableViewDelegate void RUTableDataModel::tableCellTouched(TableViewSmooth* table, TableViewCell* cell) { if(_tableCellTouched) _tableCellTouched(table,cell) ; } void RUTableDataModel::tableCellTouchedHandle(TableViewSmooth* table, TableViewCell* cell, Touch *pTouch) { } void RUTableDataModel::singleCycle(int i_max,std::function callback) { for(int i=0; i<=i_max ; ++i) { if(!callback(i)) { break ; } } } void RUTableDataModel::mutiCycle(int i_max,std::function callback) { for(int i=0,cumulate_i=0 ;; i_max==i ? i=-1:0, ++i,++cumulate_i) { if(!callback(i,cumulate_i)) { break ; } } } void RUTableDataModel::checkLegality() { int cycle_body_count = 0 ; for(auto& iter : table_regular) { int count = std::get<1>(iter) ; if(count >= 0 ) { continue; } if(count == -1 ) { ++cycle_body_count ; } else { assert(0); } } if(cycle_body_count>1) { assert(0); } } void RUTableDataModel::expandConfig() { int level_max = _config.level_count ; for(auto iter : table_regular) { int cycle_count = std::abs(std::get<1>(iter)) ; for(int i=0; i(iter).begin(), std::get<0>(iter).end()) ; if((int)CA.size() >= level_max) { CA.resize(level_max) ; return ; } } } } cocos2d::Size RUTableDataModel::TableSize() { cocos2d::Size total ; if(total.equals(cocos2d::Size::ZERO) || _dirty) { if(_config.layOut == LayOut::HORIZONTAL) { total.height = CA[0].cell_size.height ; for(auto& iter : CA) { total.width += iter.cell_size.width ; } } else { total.width = CA[0].cell_size.width ; for(auto& iter : CA) { total.height += iter.cell_size.height ; } } } return total ; } int RUTableDataModel::FrameCount() { int total = 0 ; if(total == 0 || _dirty) { for(auto& iter : CA) { total+=iter.frame_count ; } } return total ; } int RUTableDataModel::CellCount() { int total = 0 ; if(total == 0 || _dirty) { total = (int)CA.size() ; } return total ; } int RUTableDataModel::CellCount(int in_frameGlobalIndex) { int out_cellCnt=0 ; singleCycle((int)CA.size()-1, [&](int i)->bool { in_frameGlobalIndex -= CA[i].frame_count ; ++out_cellCnt ; if(in_frameGlobalIndex<=0) { return false; } return true ; }); if(in_frameGlobalIndex<=0) { return out_cellCnt; } else { assert(0) ; } } bool RUTableDataModel::checkCellExist(int cellIndex) { if(cellIndex+1>CellCount()) { CCLOG("指定cell不存在"); assert(0) ; return false; } return true ; } bool RUTableDataModel::checkFrameExist(int frameIndex) { if(frameIndex+1>FrameCount()) { CCLOG("指定frame不存在"); assert(0) ; return false; } return true ; } int RUTableDataModel::FrameNeedCountForFullCell(int in_visibleFrames) { // checkFrameExist(in_visibleFrames-1) ; int out_add2FullCell = 0 ; singleCycle((int)CA.size()-1, [&](int i)->bool { CCLOG("get_add2FullCell_head"); in_visibleFrames -= CA[i].frame_count ; if(in_visibleFrames<0) { out_add2FullCell = -in_visibleFrames ; return false ; } return true ; }) ; if(in_visibleFrames>=0) { assert(0); } return out_add2FullCell; } void RUTableDataModel::get_cell_and_localFrameIndex_by_globalFrameIndex(int& cellIndex,int& localFrameIndex,int globalFrameIndex) { checkFrameExist(globalFrameIndex) ; singleCycle((int)CA.size()-1, [&](int i)->bool { CCLOG("get_cellIndex_and_fIdx"); int remain = (globalFrameIndex -= CA[i].frame_count); if(remain < 0 ) { cellIndex = i ; localFrameIndex = CA[i].frame_count + remain ; return false ; } return true ; }) ; }; void RUTableDataModel::getOffsetByCellGlobalIndex(int cellGlobalIndex,float& out_offsetX) { checkCellExist(cellGlobalIndex) ; out_offsetX = .0f ; singleCycle((int)CA.size()-1, [&](int i)->bool { if(i>cellGlobalIndex) { return false ; } out_offsetX += CA[i].cell_size.width; return true; }); } void RUTableDataModel::getCellWidth(int cellGlobalIndex,float& out_cellWidth) { checkCellExist(cellGlobalIndex) ; out_cellWidth = .0f ; out_cellWidth = CA[cellGlobalIndex].cell_size.width ; } void RUTableDataModel::getGlobalIndexForFirstFrameInCell(int idx,int& out_startIdx) { checkCellExist(idx) ; out_startIdx= 0 ; int temp_idx = -1 ; singleCycle((int)CA.size()-1, [&](int i)->bool { ++temp_idx ; if(temp_idx==idx) { return false; } else { out_startIdx += CA[i].frame_count ; } return true ; }); } void RUTableDataModel::getCellIndexByFrameGlobalIndex(int in_frameGlobalIndex,int& out_cellIndex) { out_cellIndex = 0 ; singleCycle((int)CA.size()-1, [&](int i)->bool{ in_frameGlobalIndex -= CA[i].frame_count ; if(in_frameGlobalIndex<0) { ++out_cellIndex ; return false ; } else { ++out_cellIndex ; } return true ; }) ; } void RUTableDataModel::get_type_and_count_by_cellIdx(int cellGlobalIndex,int& out_frameCount,std::string & out_frameType) { checkCellExist(cellGlobalIndex) ; out_frameCount = 0 ; out_frameType = CA[cellGlobalIndex].frameType ; out_frameCount = (int)CA[cellGlobalIndex].frame_count; } std::string RUTableDataModel::getCellCCB(int cellGlobalIndex) { checkCellExist(cellGlobalIndex); return CA[cellGlobalIndex].cellCCB ; } NS_RU_END