Пример #1
0
void ExpandCelCanvas::validateSourceCanvas(const gfx::Region& rgn)
{
  getSourceCanvas();

  gfx::Region rgnToValidate(rgn);
  rgnToValidate.offset(-m_bounds.getOrigin());
  rgnToValidate.createSubtraction(rgnToValidate, m_validSrcRegion);
  rgnToValidate.createIntersection(rgnToValidate, gfx::Region(m_srcImage->bounds()));

  if (m_celImage) {
    gfx::Region rgnToClear;
    rgnToClear.createSubtraction(rgnToValidate,
      gfx::Region(m_celImage->bounds()
        .offset(m_origCelPos)
        .offset(-m_bounds.getOrigin())));
    for (const auto& rc : rgnToClear)
      fill_rect(m_srcImage, rc, m_srcImage->maskColor());

    for (const auto& rc : rgnToValidate)
      m_srcImage->copy(m_celImage, rc.x, rc.y,
        rc.x+m_bounds.x-m_origCelPos.x,
        rc.y+m_bounds.y-m_origCelPos.y, rc.w, rc.h);
  }
  else {
    for (const auto& rc : rgnToValidate)
      fill_rect(m_srcImage, rc, m_srcImage->maskColor());
  }

  m_validSrcRegion.createUnion(m_validSrcRegion, rgnToValidate);
}
Пример #2
0
void ExpandCelCanvas::commit()
{
  ASSERT(!m_closed);
  ASSERT(!m_committed);

  if (!m_layer) {
    m_committed = true;
    return;
  }

  // Was the cel created in the start of the tool-loop?
  if (m_celCreated) {
    ASSERT(m_cel);
    ASSERT(!m_celImage);

    // Validate the whole m_dstImage (invalid areas are cleared, as we
    // don't have a m_celImage)
    validateDestCanvas(gfx::Region(m_bounds));

    // We can temporary remove the cel.
    if (m_layer->isImage()) {
      static_cast<LayerImage*>(m_layer)->removeCel(m_cel);

      // Add a copy of m_dstImage in the sprite's image stock
      gfx::Rect trimBounds = getTrimDstImageBounds();
      if (!trimBounds.isEmpty()) {
        ImageRef newImage(trimDstImage(trimBounds));
        ASSERT(newImage);

        m_cel->data()->setImage(newImage);
        m_cel->setPosition(m_cel->position() + trimBounds.origin());

        // And finally we add the cel again in the layer.
        m_transaction.execute(new cmd::AddCel(m_layer, m_cel));
      }
    }
    // We are selecting inside a layer group...
    else {
      // Just delete the created layer
      delete m_cel;
      m_cel = nullptr;
    }
  }
  else if (m_celImage) {
    // Restore cel position to its original position
    m_cel->setPosition(m_origCelPos);

    ASSERT(m_cel->image() == m_celImage.get());

    gfx::Region* regionToPatch = &m_validDstRegion;
    gfx::Region reduced;

    if (m_canCompareSrcVsDst) {
      ASSERT(gfx::Region().createSubtraction(m_validDstRegion, m_validSrcRegion).isEmpty());

      for (gfx::Rect rc : m_validDstRegion) {
        if (algorithm::shrink_bounds2(getSourceCanvas(),
                                      getDestCanvas(), rc, rc)) {
          reduced |= gfx::Region(rc);
        }
      }

      regionToPatch = &reduced;
    }

    if (m_layer->isBackground()) {
      m_transaction.execute(
        new cmd::CopyRegion(
          m_cel->image(),
          m_dstImage.get(),
          *regionToPatch,
          m_bounds.origin()));
    }
    else {
      m_transaction.execute(
        new cmd::PatchCel(
          m_cel,
          m_dstImage.get(),
          *regionToPatch,
          m_bounds.origin()));
    }
  }
  else {
    ASSERT(false);
  }

  m_committed = true;
}