bool SVGTextQuery::characterNumberAtPositionCallback(Data* queryData, const SVGTextFragment& fragment) const { CharacterNumberAtPositionData* data = static_cast<CharacterNumberAtPositionData*>(queryData); // Test the query point against the bounds of the entire fragment first. FloatRect fragmentExtents = calculateFragmentBoundaries(*queryData->textRenderer, fragment); if (!fragmentExtents.contains(data->position)) return false; // Iterate through the glyphs in this fragment, and check if their extents // contain the query point. FloatRect extent; const Vector<SVGTextMetrics>& textMetrics = queryData->textRenderer->layoutAttributes()->textMetricsValues(); unsigned textMetricsOffset = fragment.metricsListOffset; unsigned fragmentOffset = 0; while (fragmentOffset < fragment.length) { calculateGlyphBoundaries(queryData, fragment, fragmentOffset, extent); if (extent.contains(data->position)) { // Compute the character offset of the glyph within the text box // and add to processedCharacters. unsigned characterOffset = fragment.characterOffset + fragmentOffset; data->processedCharacters += characterOffset - data->textBox->start(); return true; } fragmentOffset += textMetrics[textMetricsOffset].length(); textMetricsOffset++; } return false; }
static bool characterNumberAtPositionCallback(QueryData* queryData, const SVGTextFragment& fragment) { CharacterNumberAtPositionData* data = static_cast<CharacterNumberAtPositionData*>(queryData); // Test the query point against the bounds of the entire fragment first. FloatRect fragmentExtents = calculateFragmentBoundaries(*queryData->textLayoutObject, fragment); if (!fragmentExtents.contains(data->position)) return false; // Iterate through the glyphs in this fragment, and check if their extents // contain the query point. FloatRect extent; const Vector<SVGTextMetrics>& textMetrics = queryData->textLayoutObject->layoutAttributes()->textMetricsValues(); unsigned textMetricsOffset = fragment.metricsListOffset; unsigned fragmentOffset = 0; while (fragmentOffset < fragment.length) { calculateGlyphBoundaries(queryData, fragment, fragmentOffset, extent); if (extent.contains(data->position)) { // Compute the character offset of the glyph within the text node. unsigned offsetInBox = fragment.characterOffset - queryData->textBox->start() + fragmentOffset; data->offsetInTextNode = logicalOffsetInTextNode(*queryData->textLayoutObject, queryData->textBox, offsetInBox); data->hitLayoutObject = data->textLayoutObject; return true; } fragmentOffset += textMetrics[textMetricsOffset].length(); textMetricsOffset++; } return false; }
int Environment::CheckforColisionwithTrees(Player &p) { for (unsigned int i = 0; i < TreeLocations.size() ; i++ ) //TO DO Change to an iterators Loop { Tree.setPosition(TreeLocations.at(i).at(0), TreeLocations.at(i).at(1)); TreeBounds = Tree.getGlobalBounds(); // Player.Direction x=0 y=1 TreeBounds.left = TreeBounds.left + 18; TreeBounds.top = TreeBounds.top + 47; TreeBounds.width -= 28; TreeBounds.height -= 47; FloatRect CollisionArea; if (TreeBounds.intersects(p.Bounds , CollisionArea)) { if (CollisionArea.width > CollisionArea.height) { //Collision is ether form top or bottom if (CollisionArea.contains({CollisionArea.left , p.psprite.getPosition().y})) { //Something is Coliding with the Bottom of the Tree return 8; } else { //Something is coliding with the Top of the Tree return 4; } } if (CollisionArea.width < CollisionArea.height) { //Collision is either form left or Right if (CollisionArea.contains({p.psprite.getPosition().x + p.psprite.getGlobalBounds().width - 1.f, CollisionArea.top + 1.f})) { //The Left Side of the Tree is hit return 1; } else { return 2; } } } } return 0; }
// FloatRect::intersects does not consider horizontal or vertical lines (because of isEmpty()). // So special-case handling of such lines. static bool intersectsAllowingEmpty(const FloatRect& r, const FloatRect& other) { if (r.isEmpty() && other.isEmpty()) return false; if (r.isEmpty() && !other.isEmpty()) { return (other.contains(r.x(), r.y()) && !other.contains(r.maxX(), r.maxY())) || (!other.contains(r.x(), r.y()) && other.contains(r.maxX(), r.maxY())); } if (other.isEmpty() && !r.isEmpty()) return intersectsAllowingEmpty(other, r); return r.intersects(other); }
void MainPerson::takeItem(Field &field, vector<Item> &items, float x, float y) { if (findItem->typeItem != emptyItem->typeItem) { if (isInUseField(x, y, true)) { ////////////////////////////////////////////////////////////////////////////////////////////////////// // Если есть место if (isEmptySlot()) { //////////////////////////////////////////////////////////////////// // Если нашли предмет int levelItem = items[findItemFromList].currentLevel; Sprite *spriteItem = items[findItemFromList].mainSprite; FloatRect objectItem = spriteItem->getGlobalBounds(); if (objectItem.contains(x, y) && levelItem == currentLevelFloor + 1) { // Перемещаем в инвентарь printf("added!1\n"); itemFromPanelQuickAccess[emptySlot] = items[findItemFromList]; itemFromPanelQuickAccess[emptySlot].mainSprite->scale(normalSize); // Удаляем из мира items.erase(items.begin() + findItemFromList); } //////////////////////////////////////////////////////////////////// } ////////////////////////////////////////////////////////////////////////////////////////////////////// } } }
bool SVGSVGElement::checkIntersectionOrEnclosure( const SVGElement& element, const FloatRect& rect, CheckIntersectionOrEnclosure mode) const { LayoutObject* layoutObject = element.layoutObject(); ASSERT(!layoutObject || layoutObject->style()); if (!layoutObject || layoutObject->style()->pointerEvents() == EPointerEvents::None) return false; if (!isIntersectionOrEnclosureTarget(layoutObject)) return false; AffineTransform ctm = toSVGGraphicsElement(element).computeCTM( AncestorScope, DisallowStyleUpdate, this); FloatRect mappedRepaintRect = ctm.mapRect(layoutObject->visualRectInLocalSVGCoordinates()); bool result = false; switch (mode) { case CheckIntersection: result = intersectsAllowingEmpty(rect, mappedRepaintRect); break; case CheckEnclosure: result = rect.contains(mappedRepaintRect); break; default: ASSERT_NOT_REACHED(); break; } return result; }
void CanvasRenderingContext2D::drawImage(HTMLImageElement* image, const FloatRect& srcRect, const FloatRect& dstRect, ExceptionCode& ec) { ASSERT(image); ec = 0; FloatRect imageRect = FloatRect(FloatPoint(), size(image)); if (!(imageRect.contains(srcRect) && srcRect.width() >= 0 && srcRect.height() >= 0 && dstRect.width() >= 0 && dstRect.height() >= 0)) { ec = INDEX_SIZE_ERR; return; } if (srcRect.isEmpty() || dstRect.isEmpty()) return; GraphicsContext* c = drawingContext(); if (!c) return; CachedImage* cachedImage = image->cachedImage(); if (!cachedImage) return; FloatRect sourceRect = c->roundToDevicePixels(srcRect); FloatRect destRect = c->roundToDevicePixels(dstRect); willDraw(destRect); #ifdef __OWB__ c->drawImage(cachedImage->image()->nativeImageForCurrentFrame(), destRect, sourceRect, state().m_globalComposite); cachedImage->image()->startAnimation(); #else c->drawImage(cachedImage->image(), destRect, sourceRect, state().m_globalComposite); #endif //__OWB__ }
bool HitTestResult::addNodeToRectBasedTestResult(Node* node, const HitTestRequest& request, const HitTestLocation& locationInContainer, const FloatRect& rect) { // If it is not a rect-based hit test, this method has to be no-op. // Return false, so the hit test stops. if (!isRectBasedTest()) return false; // If node is null, return true so the hit test can continue. if (!node) return true; if (!request.allowsShadowContent()) node = node->shadowAncestorNode(); mutableRectBasedTestResult().add(node); bool regionFilled = rect.contains(locationInContainer.boundingBox()); // FIXME: This code (incorrectly) attempts to correct for culled inline nodes. See https://bugs.webkit.org/show_bug.cgi?id=85849. if (node->renderer()->isInline() && !regionFilled) { for (RenderObject* curr = node->renderer()->parent(); curr; curr = curr->parent()) { if (!curr->isRenderInline()) break; // We need to make sure the nodes for culled inlines get included. RenderInline* currInline = toRenderInline(curr); if (currInline->alwaysCreateLineBoxes()) break; if (currInline->visibleToHitTesting() && currInline->node()) mutableRectBasedTestResult().add(currInline->node()->shadowAncestorNode()); } } return !regionFilled; }
void Image::drawTiled(GraphicsContext* ctxt, const FloatRect& destRect, const FloatPoint& srcPoint, const FloatSize& scaledTileSize, SkXfermode::Mode op, const IntSize& repeatSpacing) { FloatSize intrinsicTileSize = size(); if (hasRelativeWidth()) intrinsicTileSize.setWidth(scaledTileSize.width()); if (hasRelativeHeight()) intrinsicTileSize.setHeight(scaledTileSize.height()); FloatSize scale(scaledTileSize.width() / intrinsicTileSize.width(), scaledTileSize.height() / intrinsicTileSize.height()); FloatSize actualTileSize(scaledTileSize.width() + repeatSpacing.width(), scaledTileSize.height() + repeatSpacing.height()); FloatRect oneTileRect; oneTileRect.setX(destRect.x() + fmodf(fmodf(-srcPoint.x(), actualTileSize.width()) - actualTileSize.width(), actualTileSize.width())); oneTileRect.setY(destRect.y() + fmodf(fmodf(-srcPoint.y(), actualTileSize.height()) - actualTileSize.height(), actualTileSize.height())); oneTileRect.setSize(scaledTileSize); // Check and see if a single draw of the image can cover the entire area we are supposed to tile. if (oneTileRect.contains(destRect)) { FloatRect visibleSrcRect; visibleSrcRect.setX((destRect.x() - oneTileRect.x()) / scale.width()); visibleSrcRect.setY((destRect.y() - oneTileRect.y()) / scale.height()); visibleSrcRect.setWidth(destRect.width() / scale.width()); visibleSrcRect.setHeight(destRect.height() / scale.height()); ctxt->drawImage(this, destRect, visibleSrcRect, op, DoNotRespectImageOrientation); return; } FloatRect tileRect(FloatPoint(), intrinsicTileSize); drawPattern(ctxt, tileRect, scale, oneTileRect.location(), op, destRect, repeatSpacing); startAnimation(); }
bool HitTestResult::addNodeToRectBasedTestResult(Node* node, const LayoutPoint& pointInContainer, const FloatRect& rect) { // If it is not a rect-based hit test, this method has to be no-op. // Return false, so the hit test stops. if (!isRectBasedTest()) return false; // If node is null, return true so the hit test can continue. if (!node) return true; if (m_shadowContentFilterPolicy == DoNotAllowShadowContent) node = node->shadowAncestorNode(); mutableRectBasedTestResult().add(node); if (node->renderer()->isInline()) { for (RenderObject* curr = node->renderer()->parent(); curr; curr = curr->parent()) { if (!curr->isRenderInline()) break; // We need to make sure the nodes for culled inlines get included. RenderInline* currInline = toRenderInline(curr); if (currInline->alwaysCreateLineBoxes()) break; if (currInline->visibleToHitTesting() && currInline->node()) mutableRectBasedTestResult().add(currInline->node()->shadowAncestorNode()); } } return !rect.contains(rectForPoint(pointInContainer)); }
bool SVGSVGElement::checkEnclosure(SVGElement* element, const FloatRect& rect) { // TODO : take into account pointer-events? // FIXME: Why is element ignored?? // FIXME: Implement me (see bug 11274) return rect.contains(getBBox()); }
void CanvasRenderingContext2D::drawImage(HTMLImageElement* image, const FloatRect& srcRect, const FloatRect& dstRect, ExceptionCode& ec) { ASSERT(image); ec = 0; FloatRect imageRect = FloatRect(FloatPoint(), size(image)); if (!(imageRect.contains(srcRect) && srcRect.width() >= 0 && srcRect.height() >= 0 && dstRect.width() >= 0 && dstRect.height() >= 0)) { ec = INDEX_SIZE_ERR; return; } if (srcRect.isEmpty() || dstRect.isEmpty()) return; GraphicsContext* c = drawingContext(); if (!c) return; CachedImage* cachedImage = image->cachedImage(); if (!cachedImage) return; if (m_canvas->originClean()) checkOrigin(KURL(cachedImage->url())); FloatRect sourceRect = c->roundToDevicePixels(srcRect); FloatRect destRect = c->roundToDevicePixels(dstRect); willDraw(destRect); c->drawImage(cachedImage->image(), destRect, sourceRect, state().m_globalComposite); }
void Image::drawTiled(GraphicsContext& ctxt, const FloatRect& destRect, const FloatPoint& srcPoint, const FloatSize& scaledTileSize, SkBlendMode op, const FloatSize& repeatSpacing) { FloatSize intrinsicTileSize = FloatSize(size()); if (hasRelativeSize()) { intrinsicTileSize.setWidth(scaledTileSize.width()); intrinsicTileSize.setHeight(scaledTileSize.height()); } FloatSize scale(scaledTileSize.width() / intrinsicTileSize.width(), scaledTileSize.height() / intrinsicTileSize.height()); const FloatRect oneTileRect = computeTileContaining( destRect.location(), scaledTileSize, srcPoint, repeatSpacing); // Check and see if a single draw of the image can cover the entire area we // are supposed to tile. if (oneTileRect.contains(destRect)) { const FloatRect visibleSrcRect = computeSubsetForTile(oneTileRect, destRect, intrinsicTileSize); ctxt.drawImage(this, destRect, &visibleSrcRect, op, DoNotRespectImageOrientation); return; } FloatRect tileRect(FloatPoint(), intrinsicTileSize); drawPattern(ctxt, tileRect, scale, oneTileRect.location(), op, destRect, repeatSpacing); startAnimation(); }
bool RenderSVGModelObject::checkEnclosure(RenderObject* renderer, const FloatRect& rect) { if (!renderer || renderer->style()->pointerEvents() == PE_NONE) return false; if (!isGraphicsElement(renderer)) return false; AffineTransform ctm; getElementCTM(static_cast<SVGElement*>(renderer->node()), ctm); return rect.contains(ctm.mapRect(renderer->repaintRectInLocalCoordinates())); }
bool RenderSVGModelObject::checkEnclosure(RenderElement* renderer, const FloatRect& rect) { if (!renderer || renderer->style().pointerEvents() == PE_NONE) return false; if (!isGraphicsElement(*renderer)) return false; AffineTransform ctm; SVGElement* svgElement = downcast<SVGElement>(renderer->element()); getElementCTM(svgElement, ctm); ASSERT(svgElement->renderer()); return rect.contains(ctm.mapRect(svgElement->renderer()->repaintRectInLocalCoordinates())); }
bool RenderEmbeddedObject::isInUnavailablePluginIndicator(const LayoutPoint& point) const { FloatRect contentRect; Path path; FloatRect replacementTextRect; FloatRect arrowRect; Font font; TextRun run(""); float textWidth; return getReplacementTextGeometry(IntPoint(), contentRect, path, replacementTextRect, arrowRect, font, run, textWidth) && (path.contains(point) || arrowRect.contains(point)); }
bool RenderEmbeddedObject::isInUnavailablePluginIndicator(const FloatPoint& point) const { FloatRect contentRect; FloatRect indicatorRect; FloatRect replacementTextRect; FloatRect arrowRect; FontCascade font; TextRun run(emptyString()); float textWidth; return getReplacementTextGeometry(IntPoint(), contentRect, indicatorRect, replacementTextRect, arrowRect, font, run, textWidth) && indicatorRect.contains(point); }
FloatRect Image::computeSubsetForTile(const FloatRect& tile, const FloatRect& dest, const FloatSize& imageSize) { DCHECK(tile.contains(dest)); const FloatSize scale(tile.width() / imageSize.width(), tile.height() / imageSize.height()); FloatRect subset = dest; subset.setX((dest.x() - tile.x()) / scale.width()); subset.setY((dest.y() - tile.y()) / scale.height()); subset.setWidth(dest.width() / scale.width()); subset.setHeight(dest.height() / scale.height()); return subset; }
bool HitTestResult::addNodeToRectBasedTestResult(Node* node, const HitTestRequest& request, const HitTestLocation& locationInContainer, const FloatRect& rect) { // If it is not a rect-based hit test, this method has to be no-op. // Return false, so the hit test stops. if (!isRectBasedTest()) return false; // If node is null, return true so the hit test can continue. if (!node) return true; mutableRectBasedTestResult().add(node); bool regionFilled = rect.contains(locationInContainer.boundingBox()); return !regionFilled; }
void Entity::searchItem(vector<Item> &items, Vector2f pos) { int levelItem = items[founds.findItemFromList].currentLevel; Sprite *spriteItem = items[founds.findItemFromList].mainSprite; FloatRect objectItem = spriteItem->getGlobalBounds(); bool onOneLevel = levelItem == currentLevelFloor + 1; bool itemIsFind = objectItem.contains(pos.x, pos.y) && onOneLevel; if (itemIsFind) { transferInInventory(items); items.erase(items.begin() + founds.findItemFromList); } }
PositionWithAffinity LayoutSVGInlineText::positionForPoint(const LayoutPoint& point) { if (!hasTextBoxes() || !textLength()) return createPositionWithAffinity(0); ASSERT(m_scalingFactor); float baseline = m_scaledFont.getFontMetrics().floatAscent() / m_scalingFactor; LayoutBlock* containingBlock = this->containingBlock(); ASSERT(containingBlock); // Map local point to absolute point, as the character origins stored in the text fragments use absolute coordinates. FloatPoint absolutePoint(point); absolutePoint.moveBy(containingBlock->location()); float closestDistance = std::numeric_limits<float>::max(); float closestDistancePosition = 0; const SVGTextFragment* closestDistanceFragment = nullptr; SVGInlineTextBox* closestDistanceBox = nullptr; for (InlineTextBox* box = firstTextBox(); box; box = box->nextTextBox()) { if (!box->isSVGInlineTextBox()) continue; SVGInlineTextBox* textBox = toSVGInlineTextBox(box); for (const SVGTextFragment& fragment : textBox->textFragments()) { FloatRect fragmentRect = fragment.boundingBox(baseline); float distance = 0; if (!fragmentRect.contains(absolutePoint)) distance = fragmentRect.squaredDistanceTo(absolutePoint); if (distance <= closestDistance) { closestDistance = distance; closestDistanceBox = textBox; closestDistanceFragment = &fragment; closestDistancePosition = fragmentRect.x(); } } } if (!closestDistanceFragment) return createPositionWithAffinity(0); int offset = closestDistanceBox->offsetForPositionInFragment(*closestDistanceFragment, LayoutUnit(absolutePoint.x() - closestDistancePosition), true); return createPositionWithAffinity(offset + closestDistanceBox->start(), offset > 0 ? VP_UPSTREAM_IF_POSSIBLE : TextAffinity::Downstream); }
void Image::drawTiled(GraphicsContext* ctxt, const FloatRect& destRect, const FloatPoint& srcPoint, const FloatSize& scaledTileSize, ColorSpace styleColorSpace, CompositeOperator op) { if (mayFillWithSolidColor()) { fillWithSolidColor(ctxt, destRect, solidColor(), styleColorSpace, op); return; } // See <https://webkit.org/b/59043>. #if !PLATFORM(WX) ASSERT(!isBitmapImage() || notSolidColor()); #endif FloatSize intrinsicTileSize = size(); if (hasRelativeWidth()) intrinsicTileSize.setWidth(scaledTileSize.width()); if (hasRelativeHeight()) intrinsicTileSize.setHeight(scaledTileSize.height()); FloatSize scale(scaledTileSize.width() / intrinsicTileSize.width(), scaledTileSize.height() / intrinsicTileSize.height()); FloatRect oneTileRect; oneTileRect.setX(destRect.x() + fmodf(fmodf(-srcPoint.x(), scaledTileSize.width()) - scaledTileSize.width(), scaledTileSize.width())); oneTileRect.setY(destRect.y() + fmodf(fmodf(-srcPoint.y(), scaledTileSize.height()) - scaledTileSize.height(), scaledTileSize.height())); oneTileRect.setSize(scaledTileSize); // Check and see if a single draw of the image can cover the entire area we are supposed to tile. if (oneTileRect.contains(destRect)) { FloatRect visibleSrcRect; visibleSrcRect.setX((destRect.x() - oneTileRect.x()) / scale.width()); visibleSrcRect.setY((destRect.y() - oneTileRect.y()) / scale.height()); visibleSrcRect.setWidth(destRect.width() / scale.width()); visibleSrcRect.setHeight(destRect.height() / scale.height()); draw(ctxt, destRect, visibleSrcRect, styleColorSpace, op); return; } AffineTransform patternTransform = AffineTransform().scaleNonUniform(scale.width(), scale.height()); FloatRect tileRect(FloatPoint(), intrinsicTileSize); drawPattern(ctxt, tileRect, patternTransform, oneTileRect.location(), styleColorSpace, op, destRect); startAnimation(); }
bool SVGTextQuery::characterNumberAtPositionCallback(Data* queryData, const SVGTextFragment& fragment) const { CharacterNumberAtPositionData* data = static_cast<CharacterNumberAtPositionData*>(queryData); FloatRect extent; for (unsigned i = 0; i < fragment.length; ++i) { int startPosition = data->processedCharacters + i; int endPosition = startPosition + 1; if (!mapStartEndPositionsIntoFragmentCoordinates(queryData, fragment, startPosition, endPosition)) continue; calculateGlyphBoundaries(queryData, fragment, startPosition, extent); if (extent.contains(data->position)) { data->processedCharacters += i; return true; } } return false; }
void Image::drawTiled(GraphicsContext* ctxt, const FloatRect& destRect, const FloatPoint& srcPoint, const FloatSize& scaledTileSize, ColorSpace styleColorSpace, CompositeOperator op, BlendMode blendMode) { if (mayFillWithSolidColor()) { fillWithSolidColor(ctxt, destRect, solidColor(), styleColorSpace, op); return; } ASSERT(!isBitmapImage() || notSolidColor()); FloatSize intrinsicTileSize = size(); if (hasRelativeWidth()) intrinsicTileSize.setWidth(scaledTileSize.width()); if (hasRelativeHeight()) intrinsicTileSize.setHeight(scaledTileSize.height()); FloatSize scale(scaledTileSize.width() / intrinsicTileSize.width(), scaledTileSize.height() / intrinsicTileSize.height()); FloatRect oneTileRect; FloatSize actualTileSize(scaledTileSize.width() + spaceSize().width(), scaledTileSize.height() + spaceSize().height()); oneTileRect.setX(destRect.x() + fmodf(fmodf(-srcPoint.x(), actualTileSize.width()) - actualTileSize.width(), actualTileSize.width())); oneTileRect.setY(destRect.y() + fmodf(fmodf(-srcPoint.y(), actualTileSize.height()) - actualTileSize.height(), actualTileSize.height())); oneTileRect.setSize(scaledTileSize); // Check and see if a single draw of the image can cover the entire area we are supposed to tile. if (oneTileRect.contains(destRect) && !ctxt->drawLuminanceMask()) { FloatRect visibleSrcRect; visibleSrcRect.setX((destRect.x() - oneTileRect.x()) / scale.width()); visibleSrcRect.setY((destRect.y() - oneTileRect.y()) / scale.height()); visibleSrcRect.setWidth(destRect.width() / scale.width()); visibleSrcRect.setHeight(destRect.height() / scale.height()); draw(ctxt, destRect, visibleSrcRect, styleColorSpace, op, blendMode, ImageOrientationDescription()); return; } AffineTransform patternTransform = AffineTransform().scaleNonUniform(scale.width(), scale.height()); FloatRect tileRect(FloatPoint(), intrinsicTileSize); drawPattern(ctxt, tileRect, patternTransform, oneTileRect.location(), styleColorSpace, op, destRect, blendMode); startAnimation(); }
void Image::drawTiled(GraphicsContext* ctxt, const FloatRect& destRect, const FloatPoint& srcPoint, const FloatSize& scaledTileSize, CompositeOperator op, WebBlendMode blendMode, const IntSize& repeatSpacing) { if (mayFillWithSolidColor()) { fillWithSolidColor(ctxt, destRect, solidColor(), op); return; } // See <https://webkit.org/b/59043>. ASSERT(!isBitmapImage() || notSolidColor()); FloatSize intrinsicTileSize = size(); if (hasRelativeWidth()) intrinsicTileSize.setWidth(scaledTileSize.width()); if (hasRelativeHeight()) intrinsicTileSize.setHeight(scaledTileSize.height()); FloatSize scale(scaledTileSize.width() / intrinsicTileSize.width(), scaledTileSize.height() / intrinsicTileSize.height()); FloatSize actualTileSize(scaledTileSize.width() + repeatSpacing.width(), scaledTileSize.height() + repeatSpacing.height()); FloatRect oneTileRect; oneTileRect.setX(destRect.x() + fmodf(fmodf(-srcPoint.x(), actualTileSize.width()) - actualTileSize.width(), actualTileSize.width())); oneTileRect.setY(destRect.y() + fmodf(fmodf(-srcPoint.y(), actualTileSize.height()) - actualTileSize.height(), actualTileSize.height())); oneTileRect.setSize(scaledTileSize); // Check and see if a single draw of the image can cover the entire area we are supposed to tile. if (oneTileRect.contains(destRect)) { FloatRect visibleSrcRect; visibleSrcRect.setX((destRect.x() - oneTileRect.x()) / scale.width()); visibleSrcRect.setY((destRect.y() - oneTileRect.y()) / scale.height()); visibleSrcRect.setWidth(destRect.width() / scale.width()); visibleSrcRect.setHeight(destRect.height() / scale.height()); draw(ctxt, destRect, visibleSrcRect, op, blendMode); return; } FloatRect tileRect(FloatPoint(), intrinsicTileSize); drawPattern(ctxt, tileRect, scale, oneTileRect.location(), op, destRect, blendMode, repeatSpacing); startAnimation(); }
void Image::drawTiled(GraphicsContext* ctxt, const FloatRect& destRect, const FloatPoint& srcPoint, const FloatSize& scaledTileSize, CompositeOperator op) { if (mayFillWithSolidColor()) { fillWithSolidColor(ctxt, destRect, solidColor(), op); return; } FloatSize intrinsicTileSize = size(); if (hasRelativeWidth()) intrinsicTileSize.setWidth(scaledTileSize.width()); if (hasRelativeHeight()) intrinsicTileSize.setHeight(scaledTileSize.height()); FloatSize scale(scaledTileSize.width() / intrinsicTileSize.width(), scaledTileSize.height() / intrinsicTileSize.height()); AffineTransform patternTransform = AffineTransform().scale(scale.width(), scale.height()); FloatRect oneTileRect; oneTileRect.setX(destRect.x() + fmodf(fmodf(-srcPoint.x(), scaledTileSize.width()) - scaledTileSize.width(), scaledTileSize.width())); oneTileRect.setY(destRect.y() + fmodf(fmodf(-srcPoint.y(), scaledTileSize.height()) - scaledTileSize.height(), scaledTileSize.height())); oneTileRect.setSize(scaledTileSize); // Check and see if a single draw of the image can cover the entire area we are supposed to tile. if (oneTileRect.contains(destRect)) { FloatRect visibleSrcRect; visibleSrcRect.setX((destRect.x() - oneTileRect.x()) / scale.width()); visibleSrcRect.setY((destRect.y() - oneTileRect.y()) / scale.height()); visibleSrcRect.setWidth(destRect.width() / scale.width()); visibleSrcRect.setHeight(destRect.height() / scale.height()); draw(ctxt, destRect, visibleSrcRect, op); return; } FloatRect tileRect(FloatPoint(), intrinsicTileSize); drawPatternCounter.startCounting(); drawPattern(ctxt, tileRect, patternTransform, oneTileRect.location(), op, destRect); drawPatternCounter.stopCounting(); startAnimation(); }
void CanvasRenderingContext2D::drawImage(HTMLVideoElement* video, const FloatRect& srcRect, const FloatRect& dstRect, ExceptionCode& ec) { ASSERT(video); ec = 0; FloatRect videoRect = FloatRect(FloatPoint(), size(video)); if (!videoRect.contains(normalizeRect(srcRect)) || srcRect.width() == 0 || srcRect.height() == 0) { ec = INDEX_SIZE_ERR; return; } if (!dstRect.width() || !dstRect.height()) return; GraphicsContext* c = drawingContext(); if (!c) return; if (!state().m_invertibleCTM) return; if (canvas()->originClean()) checkOrigin(video->currentSrc()); if (canvas()->originClean() && !video->hasSingleSecurityOrigin()) canvas()->setOriginTainted(); FloatRect sourceRect = c->roundToDevicePixels(srcRect); FloatRect destRect = c->roundToDevicePixels(dstRect); willDraw(destRect); c->save(); c->clip(destRect); c->translate(destRect.x(), destRect.y()); c->scale(FloatSize(destRect.width()/sourceRect.width(), destRect.height()/sourceRect.height())); c->translate(-sourceRect.x(), -sourceRect.y()); video->paintCurrentFrameInContext(c, IntRect(IntPoint(), size(video))); c->restore(); }
Vector<FloatRect> NinePieceImage::computeIntrinsicRects(const FloatRect& outer, const LayoutBoxExtent& slices, float deviceScaleFactor) { FloatRect inner = outer; inner.move(slices.left(), slices.top()); inner.contract(slices.left() + slices.right(), slices.top() + slices.bottom()); ASSERT(outer.contains(inner)); Vector<FloatRect> rects(MaxPiece); rects[TopLeftPiece] = snapRectToDevicePixels(outer.x(), outer.y(), slices.left(), slices.top(), deviceScaleFactor); rects[BottomLeftPiece] = snapRectToDevicePixels(outer.x(), inner.maxY(), slices.left(), slices.bottom(), deviceScaleFactor); rects[LeftPiece] = snapRectToDevicePixels(outer.x(), inner.y(), slices.left(), inner.height(), deviceScaleFactor); rects[TopRightPiece] = snapRectToDevicePixels(inner.maxX(), outer.y(), slices.right(), slices.top(), deviceScaleFactor); rects[BottomRightPiece] = snapRectToDevicePixels(inner.maxX(), inner.maxY(), slices.right(), slices.bottom(), deviceScaleFactor); rects[RightPiece] = snapRectToDevicePixels(inner.maxX(), inner.y(), slices.right(), inner.height(), deviceScaleFactor); rects[TopPiece] = snapRectToDevicePixels(inner.x(), outer.y(), inner.width(), slices.top(), deviceScaleFactor); rects[BottomPiece] = snapRectToDevicePixels(inner.x(), inner.maxY(), inner.width(), slices.bottom(), deviceScaleFactor); rects[MiddlePiece] = snapRectToDevicePixels(inner.x(), inner.y(), inner.width(), inner.height(), deviceScaleFactor); return rects; }
void CanvasRenderingContext2D::drawImage(HTMLImageElement* image, const FloatRect& srcRect, const FloatRect& dstRect, ExceptionCode& ec) { ASSERT(image); ec = 0; FloatRect imageRect = FloatRect(FloatPoint(), size(image)); if (!imageRect.contains(normalizeRect(srcRect)) || srcRect.width() == 0 || srcRect.height() == 0) { ec = INDEX_SIZE_ERR; return; } if (!dstRect.width() || !dstRect.height()) return; GraphicsContext* c = drawingContext(); if (!c) return; if (!state().m_invertibleCTM) return; CachedImage* cachedImage = image->cachedImage(); if (!cachedImage) return; if (canvas()->originClean()) checkOrigin(cachedImage->response().url()); if (canvas()->originClean() && !cachedImage->image()->hasSingleSecurityOrigin()) canvas()->setOriginTainted(); FloatRect sourceRect = c->roundToDevicePixels(srcRect); FloatRect destRect = c->roundToDevicePixels(dstRect); willDraw(destRect); c->drawImage(cachedImage->image(), DeviceColorSpace, destRect, sourceRect, state().m_globalComposite); }
void CanvasRenderingContext2D::drawImage(HTMLCanvasElement* sourceCanvas, const FloatRect& srcRect, const FloatRect& dstRect, ExceptionCode& ec) { ASSERT(sourceCanvas); ec = 0; FloatRect srcCanvasRect = FloatRect(FloatPoint(), sourceCanvas->size()); if (!srcCanvasRect.contains(normalizeRect(srcRect)) || srcRect.width() == 0 || srcRect.height() == 0) { ec = INDEX_SIZE_ERR; return; } if (!dstRect.width() || !dstRect.height()) return; GraphicsContext* c = drawingContext(); if (!c) return; if (!state().m_invertibleCTM) return; FloatRect sourceRect = c->roundToDevicePixels(srcRect); FloatRect destRect = c->roundToDevicePixels(dstRect); // FIXME: Do this through platform-independent GraphicsContext API. ImageBuffer* buffer = sourceCanvas->buffer(); if (!buffer) return; if (!sourceCanvas->originClean()) canvas()->setOriginTainted(); c->drawImage(buffer->image(), DeviceColorSpace, destRect, sourceRect, state().m_globalComposite); willDraw(destRect); // This call comes after drawImage, since the buffer we draw into may be our own, and we need to make sure it is dirty. // FIXME: Arguably willDraw should become didDraw and occur after drawing calls and not before them to avoid problems like this. }