void FlowConstraintsCollection::pruneStaticFlag()

in lib/FlowConstraints.cpp [662:748]


void FlowConstraintsCollection::pruneStaticFlag(const int distance) {
  const ColorStream& downStream = video_->colorStream("down");
  const int w = downStream.width();
  const int h = downStream.height();

  std::vector<Mat1b> masks(video_->numFrames());

  Mat1b diskMask = buildDiskMask(distance);

  for (int frame = 0; frame < video_->numFrames(); ++frame) {
    Mat1b& mask = masks[frame];
    mask.create(h, w);
    mask = 0;

    for (auto it = pairBegin(); it != pairEnd(); it++) {
      const PairKey& key = *it;
      if (key.first != frame && key.second != frame) {
        continue;
      }

      std::unique_ptr<PairFlowConstraints>& pairConstraints = pairs_.at(key);
      for (PairConstraint& c : pairConstraints->constraints_) {
        if (c.isStatic) {
          continue;
        }

        Vector2fna loc = (key.first == frame ? c[0] : c[1]);
        int x = loc.x() * w;
        int y = loc.y() * w;

        const int mx0 = std::max(0, x - distance);
        const int mx1 = std::min(w - 1, x + distance);
        const int my0 = std::max(0, y - distance);
        const int my1 = std::min(h - 1, y + distance);
        for (int my = my0; my <= my1; ++my) {
          const int dy = my - (y - distance);
          const uint8_t* diskPtr = diskMask.ptr<const uint8_t>(dy);
          uint8_t* maskPtr = mask.ptr<uint8_t>(my);
          for (int mx = mx0; mx <= mx1; ++mx) {
            const int dx = mx - (x - distance);
            if (diskPtr[dx]) {
              maskPtr[mx] = 255;
            }
          }
        }
      }
    }
  }

  for (auto it = pairBegin(); it != pairEnd(); it++) {
    const PairKey& key = *it;

    const Mat1b& mask0 = masks[key.first];
    const Mat1b& mask1 = masks[key.second];

    std::unique_ptr<PairFlowConstraints>& pairConstraints = pairs_.at(key);
    for (PairConstraint& c : pairConstraints->constraints_) {
      Vector2i p0(c[0].x() * w, c[0].y() * w);
      Vector2i p1(c[1].x() * w, c[1].y() * w);
      if (mask0(p0.y(), p0.x()) || mask1(p1.y(), p1.x())) {
        c.isStatic = false;
      }
    }
  }

  for (auto it = tripletBegin(); it != tripletEnd(); it++) {
    const TripletKey& key = *it;

    const Mat1b& mask0 = masks[key - 1];
    const Mat1b& mask1 = masks[key];
    const Mat1b& mask2 = masks[key + 1];

    std::unique_ptr<TripletFlowConstraints>& tripletConstraints =
        triplets_.at(key);
    for (TripletConstraint& c : tripletConstraints->constraints_) {
      Vector2i p0(c[0].x() * w, c[0].y() * w);
      Vector2i p1(c[1].x() * w, c[1].y() * w);
      Vector2i p2(c[2].x() * w, c[2].y() * w);

      if (mask0(p0.y(), p0.x()) ||
          mask1(p1.y(), p1.x()) ||
          mask2(p2.y(), p2.x())) {
        c.isStatic = false;
      }
    }
  }
}