public Tuple<String, Integer> getCurrDottedStatement(ICharacterPairMatcher2 pairMatcher)
      throws BadLocationException {
    int absoluteCursorOffset = getAbsoluteCursorOffset();
    int start = absoluteCursorOffset;
    for (int i = absoluteCursorOffset - 1; i >= 0; i--) {
      char c = doc.getChar(i);
      if (!Character.isJavaIdentifierPart(c) && c != '.') {
        // We're at the start now, so, let's go onwards now...
        if (StringUtils.isClosingPeer(c)) {
          int j = pairMatcher.searchForOpeningPeer(i, StringUtils.getPeer(c), c, doc);
          if (j < 0) {
            break;
          }
          i = j;
        } else {
          break;
        }
      }
      start = i;
    }

    int len = doc.getLength();
    int end = absoluteCursorOffset;
    for (int i = absoluteCursorOffset; i < len; i++) {
      char c = doc.getChar(i);
      if (!Character.isJavaIdentifierPart(c) && c != '.') {
        if (StringUtils.isOpeningPeer(c)) {
          int j = pairMatcher.searchForClosingPeer(i, c, StringUtils.getPeer(c), doc);
          if (j < 0) {
            break;
          }
          i = j;
        } else {
          break;
        }
      }
      end = i + 1;
    }

    if (start != end) {
      return new Tuple<String, Integer>(doc.get(start, end - start), start);
    }

    return new Tuple<String, Integer>("", absoluteCursorOffset);
  }
  public int searchForAnyOpeningPeer(int offset, IDocument document) {
    try {
      fReader.configureBackwardReader(document, offset, true, true, true);

      Map<Character, Integer> stack = new HashMap<Character, Integer>();

      HashSet<Character> closing = new HashSet<Character>();
      HashSet<Character> opening = new HashSet<Character>();

      for (int i = 0; i < fPairs.length; i++) {
        stack.put(fPairs[i], 1);
        if (i % 2 == 0) {
          opening.add(fPairs[i]);
        } else {
          closing.add(fPairs[i]);
        }
      }

      int c = fReader.read();
      while (c != PythonCodeReader.EOF) {
        if (closing.contains((char) c)) { // c == ')' || c == ']' || c == '}'
          char peer = StringUtils.getPeer((char) c);
          Integer iStack = stack.get((char) peer);
          iStack++;
          stack.put(peer, iStack);

        } else if (opening.contains((char) c)) { // c == '(' || c == '[' || c == '{'
          Integer iStack = stack.get((char) c);
          iStack--;
          stack.put((char) c, iStack);

          if (iStack == 0) {
            return fReader.getOffset();
          }
        }

        c = fReader.read();
      }

      return -1;
    } catch (Exception e) {
      throw new RuntimeException(e);
    }
  }