protected Operation transform(DeleteOperation delA, InsertOperation insB) {

    int posA = delA.getPosition();
    int lenA = delA.getTextLength();
    int posB = insB.getPosition();
    int lenB = insB.getTextLength();

    if (posB >= (posA + lenA)) {
      /*
       * Operation B is completely after operation A.
       */
      return delA;
    } else if (posB <= posA) {
      /*
       * Operation B starts before or at the same position like operation
       * A
       */
      return new DeleteOperation(posA + lenB, delA.getText());
    } else {
      /*
       * Operation B (insert) is in the range of operation A (delete).
       * Operation A' must be split up into two delete operations. (A):
       * "123456" (A'): "1" "23456"
       */
      DeleteOperation del1 = new DeleteOperation(posA, delA.getText().substring(0, posB - posA));
      DeleteOperation del2 =
          new DeleteOperation(posA + lenB, delA.getText().substring(posB - posA, lenA));
      return new SplitOperation(del1, del2);
    }
  }
  protected Operation transform(
      InsertOperation insA, InsertOperation insB, boolean isTransformPrivileged) {

    int posA = insA.getPosition();
    int posB = insB.getPosition();
    int lenB = insB.getTextLength();
    if ((posA < posB)
        || ((posA == posB) && (insA.getOrigin() < insB.getOrigin()))
        || ((posA == posB) && (insA.getOrigin() == insB.getOrigin()) && isTransformPrivileged)) {
      /*
       * Operation A starts before operation B.
       */
      return insA;
    } else {
      /*
       * Operation A starts in or behind operation B. Index of operation
       * A' must be increased by the length of the text of operation B.
       */
      return new InsertOperation(posA + lenB, insA.getText(), insA.getOrigin());
    }
  }