22 using namespace ROOT::Experimental;
 
   23 namespace REX = ROOT::Experimental;
 
   34 REveSelection::REveSelection(
const std::string& n, 
const std::string& t,
 
   35                              Color_t col_visible, Color_t col_hidden) :
 
   37    fVisibleEdgeColor (col_visible),
 
   38    fHiddenEdgeColor  (col_hidden),
 
   54    AddPickToSelect(kPS_Master);
 
   55    AddPickToSelect(kPS_PableCompound);
 
   56    AddPickToSelect(kPS_Element);
 
   62 REveSelection::~REveSelection()
 
   64    DeactivateSelection();
 
   71 void REveSelection::SetVisibleEdgeColorRGB(UChar_t r, UChar_t g, UChar_t b)
 
   73    fVisibleEdgeColor = TColor::GetColor(r, g, b);
 
   79 void REveSelection::SetHiddenEdgeColorRGB(UChar_t r, UChar_t g, UChar_t b)
 
   81    fHiddenEdgeColor = TColor::GetColor(r, g, b);
 
   88 void REveSelection::SetHighlightMode()
 
  101 void REveSelection::DoElementSelect(SelMap_i &entry)
 
  103    Set_t &imp_set = entry->second.f_implied;
 
  105    entry->first->FillImpliedSelectedSet(imp_set);
 
  107    auto i = imp_set.begin();
 
  108    while (i != imp_set.end())
 
  110       if ((*i)->GetElementId() == 0)
 
  114             Info(
"REveSelection::DoElementSelect",
 
  115                  "Element '%s' [%s] with 0 id detected and removed.",
 
  116                  (*i)->GetCName(), (*i)->IsA()->GetName());
 
  123          (*i)->IncImpliedSelected();
 
  133 void REveSelection::DoElementUnselect(SelMap_i &entry)
 
  135    Set_t &imp_set = entry->second.f_implied;
 
  137    for (
auto &imp_el: imp_set) imp_el->DecImpliedSelected();
 
  145 bool REveSelection::HasNiece(REveElement *el)
 const 
  147    return fMap.find(el) != fMap.end();
 
  153 bool REveSelection::HasNieces()
 const 
  155    return ! fMap.empty();
 
  162 bool REveSelection::AcceptNiece(REveElement* el)
 
  164    return el != 
this && fMap.find(el) == fMap.end() &&
 
  165           el->IsA()->InheritsFrom(TClass::GetClass<REveSelection>()) == kFALSE;
 
  171 void REveSelection::AddNieceInternal(REveElement* el)
 
  173    auto res = fMap.emplace(el, Record(el));
 
  175       DoElementSelect(res.first);
 
  178    StampObjPropsPreChk();
 
  184 void REveSelection::RemoveNieceInternal(REveElement* el)
 
  186    auto i = fMap.find(el);
 
  192          DoElementUnselect(i);
 
  193          SelectionRemoved(el);
 
  196       StampObjPropsPreChk();
 
  200       Warning(
"REveSelection::RemoveNieceLocal", 
"element not found in map.");
 
  208 void REveSelection::RemoveNieces()
 
  210    if (IsEmpty()) 
return;
 
  212    for (
auto i = fMap.begin(); i != fMap.end(); ++i)
 
  214       i->first->RemoveAunt(
this);
 
  215       if (fActive) DoElementUnselect(i);
 
  218    if (fActive) SelectionCleared();
 
  219    StampObjPropsPreChk();
 
  229 void REveSelection::RemoveImpliedSelected(REveElement *el)
 
  231    bool changed = 
false;
 
  235       auto j = i.second.f_implied.find(el);
 
  236       if (j != i.second.f_implied.end())
 
  238          i.second.f_implied.erase(j);
 
  243    if (changed) StampObjPropsPreChk();
 
  251 void REveSelection::RecheckImpliedSet(SelMap_i &smi)
 
  253    bool  changed = 
false;
 
  255    smi->first->FillImpliedSelectedSet(set);
 
  258       if (smi->second.f_implied.find(i) == smi->second.f_implied.end())
 
  260          smi->second.f_implied.insert(i);
 
  261          i->IncImpliedSelected();
 
  266    if (changed) StampObjPropsPreChk();
 
  273 void REveSelection::RecheckImpliedSetForElement(REveElement *el)
 
  277       auto i = fMap.find(el);
 
  279          RecheckImpliedSet(i);
 
  284    if (el->GetImpliedSelected() > 0)
 
  286       for (
auto i = fMap.begin(); i != fMap.end(); ++i)
 
  288          if (i->second.f_implied.find(el) != i->second.f_implied.end())
 
  289             RecheckImpliedSet(i);
 
  297 void REveSelection::SelectionAdded(REveElement* )
 
  306 void REveSelection::SelectionRemoved(REveElement* )
 
  315 void REveSelection::SelectionCleared()
 
  324 void REveSelection::SelectionRepeated(REveElement* )
 
  333 void REveSelection::ActivateSelection()
 
  338    for (
auto i = fMap.begin(); i != fMap.end(); ++i) {
 
  340       SelectionAdded(i->first);
 
  347 void REveSelection::DeactivateSelection()
 
  349    if (!fActive) 
return;
 
  351    for (
auto i = fMap.begin(); i != fMap.end(); ++i) {
 
  352       DoElementUnselect(i);
 
  363 REveElement* REveSelection::MapPickedToSelected(REveElement* el)
 
  368    for (
int pick_to_select : fPickToSelect)
 
  370       switch (pick_to_select)
 
  380          case kPS_Projectable:
 
  382             REveProjected* pted = 
dynamic_cast<REveProjected*
>(el);
 
  384                return dynamic_cast<REveElement*
>(pted->GetProjectable());
 
  389             REveElement* cmpnd = el->GetCompound();
 
  394          case kPS_PableCompound:
 
  396             REveProjected* pted = 
dynamic_cast<REveProjected*
>(el);
 
  398                el = 
dynamic_cast<REveElement*
>(pted->GetProjectable());
 
  399             REveElement* cmpnd = el->GetCompound();
 
  408             REveElement* mstr = el->GetSelectionMaster();
 
  426 void REveSelection::UserPickedElement(REveElement* el, Bool_t multi)
 
  428    el = MapPickedToSelected(el);
 
  430    if (el || NotEmpty())
 
  449 void REveSelection::UserRePickedElement(REveElement* el)
 
  451    el = MapPickedToSelected(el);
 
  452    if (el && HasNiece(el))
 
  454       SelectionRepeated(el);
 
  463 void REveSelection::UserUnPickedElement(REveElement* el)
 
  465    el = MapPickedToSelected(el);
 
  466    if (el && HasNiece(el))
 
  475 void REveSelection::NewElementPicked(ElementId_t 
id, 
bool multi, 
bool secondary, 
const std::set<int>& secondary_idcs)
 
  477    static const REveException eh(
"REveSelection::NewElementPicked ");
 
  479    REveElement *pel = 
nullptr, *el = 
nullptr;
 
  483      pel = REX::gEve->FindElementById(
id);
 
  485      if ( ! pel) 
throw eh + 
"picked element id=" + 
id + 
" not found.";
 
  487      el = MapPickedToSelected(pel);
 
  491       std::string debug_secondary;
 
  493          debug_secondary = 
" {";
 
  494          for (
auto si : secondary_idcs) {
 
  495             debug_secondary.append(
" ");
 
  496             debug_secondary.append(std::to_string(si));
 
  498          debug_secondary.append(
" }");
 
  500       ::Info(
"REveSelection::NewElementPicked", 
"%p -> %p, multi: %d, secondary: %d  %s", pel, el, multi, secondary, debug_secondary.c_str());
 
  503    Record *rec = find_record(el);
 
  513             if (secondary || rec->is_secondary()) 
 
  548                rec->f_is_sec   = 
true;
 
  549                rec->f_sec_idcs = secondary_idcs;
 
  558             if (HasNieces()) RemoveNieces();
 
  562                rec = find_record(el);
 
  563                rec->f_is_sec   = 
true;
 
  564                rec->f_sec_idcs = secondary_idcs;
 
  584 void REveSelection::ClearSelection()
 
  598 int REveSelection::RemoveImpliedSelectedReferencesTo(REveElement *el)
 
  604       auto j = i.second.f_implied.find(el);
 
  606       if (j != i.second.f_implied.end())
 
  608          i.second.f_implied.erase(j);
 
  609          el->DecImpliedSelected();
 
  620 Int_t REveSelection::WriteCoreJson(nlohmann::json &j, Int_t )
 
  622    REveElement::WriteCoreJson(j, -1);
 
  624    j[
"fVisibleEdgeColor"] = fVisibleEdgeColor;
 
  625    j[
"fHiddenEdgeColor"]  = fHiddenEdgeColor;
 
  627    nlohmann::json sel_list = nlohmann::json::array();
 
  631       nlohmann::json rec = {}, imp = nlohmann::json::array(), sec = nlohmann::json::array();
 
  633       rec[
"primary"] = i.first->GetElementId();
 
  636       for (
auto &imp_el : i.second.f_implied) imp.push_back(imp_el->GetElementId());
 
  637       rec[
"implied"]  = imp;
 
  640       for (
auto &sec_id : i.second.f_sec_idcs) sec.push_back(sec_id);
 
  641       rec[
"sec_idcs"] = sec;
 
  643       sel_list.push_back(rec);
 
  646    j[
"sel_list"] = sel_list;
 
  648    j[
"UT_PostStream"] = 
"UT_Selection_Refresh_State";