Ejemplo n.º 1
0
  /**
   * Insert an empty placeholder SDT, to facilitate round-tripping (ie ability to convert instance
   * docx back to original template), which you may wish to do if you want to insert updated data,
   * but preserve certain manual edits.
   *
   * @param sdt
   * @return
   */
  private List<Object> repeatZero(Object sdt) {

    List<Object> newContent = new ArrayList<Object>();

    //		if (removeSdtCellsOnFailedCondition) {
    //			// backward compatibility
    //			// NB this is not compatible with reverting functionality, and
    //			// will break if the result is an empty tc
    //			return newContent;
    //		}

    newContent.add(sdt);

    // Change the tag to od:resultRepeatZero
    SdtPr sdtPr = getSdtPr(sdt);

    CTDataBinding binding = sdtPr.getDataBinding();
    if (binding != null) { // Shouldn't be a binding anyway
      sdtPr.getRPrOrAliasOrLock().remove(binding);
    }

    Tag tag = sdtPr.getTag();

    final String tagVal = tag.getVal();
    final Pattern stripRepeatArgPattern = Pattern.compile("(.*od:repeat=)([^&]*)(.*)");
    final Matcher stripPatternMatcher = stripRepeatArgPattern.matcher(tagVal);
    if (!stripPatternMatcher.matches()) {
      log.error(
          "Cannot find repeat tag in sdtPr/tag while processing repeat; something is wrong with "
              + tagVal);
      return newContent;
    }
    final String emptyRepeatValue =
        BINDING_RESULT_RPTD_ZERO
            + "="
            + stripPatternMatcher.group(2)
            + stripPatternMatcher.group(3);
    tag.setVal(emptyRepeatValue);

    // Lock it
    CTLock lock = Context.getWmlObjectFactory().createCTLock();
    lock.setVal(org.docx4j.wml.STLock.SDT_CONTENT_LOCKED);
    JAXBElement<org.docx4j.wml.CTLock> lockWrapped =
        Context.getWmlObjectFactory().createSdtPrLock(lock);
    sdtPr.getRPrOrAliasOrLock().add(lockWrapped); // assumes no lock is there already

    // Empty the content
    // .. OpenDoPEIntegrity fixes this where it is not OK, but
    // where it needs to insert a tc, it has no way of adding original tcPr, so
    // we handle this here
    TcFinder tcFinder = new TcFinder();
    new TraversalUtil(((SdtElement) sdt).getSdtContent().getContent(), tcFinder);
    if (tcFinder.tcList.size() > 0) {
      Tc tc = tcFinder.tcList.get(0);
      tc.getContent().clear();
      P p = Context.getWmlObjectFactory().createP();
      tc.getContent().add(p);
      ((SdtElement) sdt).getSdtContent().getContent().clear();
      ((SdtElement) sdt).getSdtContent().getContent().add(tc);
    } else {
      ((SdtElement) sdt).getSdtContent().getContent().clear();
    }

    return newContent;
  }