如何让Canvas在Flex中剪辑其内容?

发布于 2024-07-13 11:44:15 字数 131 浏览 15 评论 0原文

我使用 moveTo 和 lineTo 图形方法在 Canvas 对象上绘制一条线。 如果线的一端位于画布之外,则线会溢出并绘制在应用程序中其他元素的上方或下方。

如何使画布将线条包含在其自身内?

谢谢!

I draw a line on a Canvas object with the moveTo and lineTo graphics methods. If one end of the line lies outside the Canvas, the line spills out and is drawn over or under other elements in the application.

How do I make the Canvas keep the line contained within itself?

Thanks!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(6

你与昨日 2024-07-20 11:44:15
<mx:Canvas id="canvas" top="0" right="51" left="0" bottom="32">
<mx:Canvas x="-1" y="0" width="0" height="0"> <!-- This is a HACK to make the canvas clip -->
</mx:Canvas>
</mx:Canvas>
<mx:Canvas id="canvas" top="0" right="51" left="0" bottom="32">
<mx:Canvas x="-1" y="0" width="0" height="0"> <!-- This is a HACK to make the canvas clip -->
</mx:Canvas>
</mx:Canvas>
瞎闹 2024-07-20 11:44:15

前段时间我也遇到过类似的问题。 您需要在画布中嵌入另一个容器,并在其中绘制原始图形。 我相信这是因为 Canvas 组件仅剪辑子组件,而不是原始图形。

示例如下: http:// /www.adobe.com/cfusion/webforums/forum/messageview.cfm?forumid=60&catid=585&threadid=1421196。 它包含一些位于页面中间位置的示例代码。

I had a similar problem some time ago. You need to embed another container inside the canvas, and draw the primitive graphics in that instead. I believe this is because the Canvas component only clips child components, and not primitive graphics.

Example here: http://www.adobe.com/cfusion/webforums/forum/messageview.cfm?forumid=60&catid=585&threadid=1421196. It includes some sample code about half way down the page.

素手挽清风 2024-07-20 11:44:15

推荐答案中的链接已损坏。 我通过在画布内放置另一个比外部画布大的画布解决了这个问题。

示例:

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" applicationComplete="onComplete()">
    <mx:Script><![CDATA[
        private function onComplete():void
        {
            canvas.graphics.lineStyle(1);
            canvas.graphics.moveTo( -100, -100);
            canvas.graphics.lineTo(400, 400);
        }
    ]]></mx:Script>
    <mx:Canvas  id="window"
                height="300" 
                width="300" 
                clipContent="true" 
                horizontalScrollPolicy="off" 
                verticalScrollPolicy="off" 
                backgroundColor="white">
        <mx:Canvas id="canvas" width="301" height="301">
        </mx:Canvas>
    </mx:Canvas>
</mx:Application>

如果要在运行时调整窗口 Canvas 的大小,请添加一个调整大小事件侦听器来调整画布 Canvas 的大小。

The link in the recommended answer is broken. I solved the problem by placing another canvas inside my canvas that is larger than the outer canvas.

Example:

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" applicationComplete="onComplete()">
    <mx:Script><![CDATA[
        private function onComplete():void
        {
            canvas.graphics.lineStyle(1);
            canvas.graphics.moveTo( -100, -100);
            canvas.graphics.lineTo(400, 400);
        }
    ]]></mx:Script>
    <mx:Canvas  id="window"
                height="300" 
                width="300" 
                clipContent="true" 
                horizontalScrollPolicy="off" 
                verticalScrollPolicy="off" 
                backgroundColor="white">
        <mx:Canvas id="canvas" width="301" height="301">
        </mx:Canvas>
    </mx:Canvas>
</mx:Application>

If the window Canvas is going to be resized at runtime, add a resize event listener to resize the canvas Canvas also.

梦里梦着梦中梦 2024-07-20 11:44:15

我刚刚开发了一个 Flex Box 组件,它充当常规组件容器,但绘制一个圆角矩形背景,另一个圆角矩形表示填充级别。 为此,我需要剪掉不应该被填充的上部部分。 将填充矩形绘制到填充高度是不可能的,因为圆角不匹配。

我学到了什么:

  • 我创建了一个 Canvas 组件,只是为了绘制边界为 0/0 和 Box 的宽度/高度的填充级别
  • 我通过 addChildAt() 将画布添加到索引 0 处的 Box
  • 我将 includeInLayout 属性设置为 false该画布,因为它不应该参与框本身的布局,而是充当顶部的一些浮动绘图窗格,
  • 然后我添加另一个画布作为该填充画布的遮罩(addChild(),并设置遮罩属性)

这里是一些代码:

override protected function updateDisplayList(unscaledWidth:Number, unscaledHeight:Number):void
{
    // super
    super.updateDisplayList(unscaledWidth, unscaledHeight);

    // prep
    var g:Graphics = this.graphics;
    var fgColor:int = this.getStyle("fillColor");
    var bgColor:int = this.getStyle("backgroundFillColor");
    var radius:int = this.getStyle("cornerRadius");

    // clear
    g.clear();

    // draw background
    g.beginFill(bgColor, 1);
    g.drawRoundRect(0, 0, unscaledWidth, unscaledHeight, radius, radius);
    g.endFill();

    // draw fill level
    if (this._fillLevel > 0) {
        var fillHeight:int = int(unscaledHeight * this._fillLevel);

        // extra component for drawing fill-level, so we can apply mask just to this
        if (this._fillLevelCanvas == null) {
            this._fillLevelCanvas = new Canvas();
            this._fillLevelCanvas.x = 0;
            this._fillLevelCanvas.y = 0;
            this._fillLevelCanvas.includeInLayout = false;
            this.addChildAt(this._fillLevelCanvas, 0);
        }
        this._fillLevelCanvas.width = unscaledWidth;
        this._fillLevelCanvas.height = unscaledHeight;

        // mask
        if (this._fillLevelMask == null) {
            this._fillLevelMask = new Canvas();
            this._fillLevelMask.x = 0;
            this._fillLevelMask.y = 0;
            this._fillLevelCanvas.addChild(this._fillLevelMask);
            this._fillLevelCanvas.mask = this._fillLevelMask;
        }
        this._fillLevelMask.width = this.width;
        this._fillLevelMask.height = this.height;
        this._fillLevelMask.graphics.beginFill(0xFFFFFF); 
        this._fillLevelMask.graphics.drawRect(0, this.height-fillHeight, this._fillLevelMask.width, this._fillLevelMask.height); 
        this._fillLevelMask.graphics.endFill();                 

        this._fillLevelCanvas.graphics.beginFill(fgColor, 1);
        this._fillLevelCanvas.graphics.drawRoundRect(0, 0, unscaledWidth, unscaledHeight, radius, radius);
        this._fillLevelCanvas.graphics.endFill();
    }
}

I have just developed a Flex Box component, which acts as a regular component container, but draws a rounded rectangle background, with another rounded rectangle indicated a fill-level. For that I needed to clip the upper section that should not get filled. Drawing the fill rectangle to the fill height was no option since the rounded corners would not match.

What I learned:

  • I created a Canvas component just for drawing the fill-level with bounds 0/0 and width/height of the Box
  • I added that canvas to the Box at index 0 via addChildAt()
  • I set the includeInLayout property to false for that canvas since it should not take part in the layouting of the Box itself but rather act as some floating drawing pane on top
  • I then added another Canvas as the mask to that fill-canvas (addChild(), and set mask property)

Here is some code:

override protected function updateDisplayList(unscaledWidth:Number, unscaledHeight:Number):void
{
    // super
    super.updateDisplayList(unscaledWidth, unscaledHeight);

    // prep
    var g:Graphics = this.graphics;
    var fgColor:int = this.getStyle("fillColor");
    var bgColor:int = this.getStyle("backgroundFillColor");
    var radius:int = this.getStyle("cornerRadius");

    // clear
    g.clear();

    // draw background
    g.beginFill(bgColor, 1);
    g.drawRoundRect(0, 0, unscaledWidth, unscaledHeight, radius, radius);
    g.endFill();

    // draw fill level
    if (this._fillLevel > 0) {
        var fillHeight:int = int(unscaledHeight * this._fillLevel);

        // extra component for drawing fill-level, so we can apply mask just to this
        if (this._fillLevelCanvas == null) {
            this._fillLevelCanvas = new Canvas();
            this._fillLevelCanvas.x = 0;
            this._fillLevelCanvas.y = 0;
            this._fillLevelCanvas.includeInLayout = false;
            this.addChildAt(this._fillLevelCanvas, 0);
        }
        this._fillLevelCanvas.width = unscaledWidth;
        this._fillLevelCanvas.height = unscaledHeight;

        // mask
        if (this._fillLevelMask == null) {
            this._fillLevelMask = new Canvas();
            this._fillLevelMask.x = 0;
            this._fillLevelMask.y = 0;
            this._fillLevelCanvas.addChild(this._fillLevelMask);
            this._fillLevelCanvas.mask = this._fillLevelMask;
        }
        this._fillLevelMask.width = this.width;
        this._fillLevelMask.height = this.height;
        this._fillLevelMask.graphics.beginFill(0xFFFFFF); 
        this._fillLevelMask.graphics.drawRect(0, this.height-fillHeight, this._fillLevelMask.width, this._fillLevelMask.height); 
        this._fillLevelMask.graphics.endFill();                 

        this._fillLevelCanvas.graphics.beginFill(fgColor, 1);
        this._fillLevelCanvas.graphics.drawRoundRect(0, 0, unscaledWidth, unscaledHeight, radius, radius);
        this._fillLevelCanvas.graphics.endFill();
    }
}
唯憾梦倾城 2024-07-20 11:44:15

将 Canvas 的 ClipToBounds 属性设置为 true:

<Canvas ClipToBounds="True">... Content ...</Canvas>

Set ClipToBounds property of the Canvas to true:

<Canvas ClipToBounds="True">... Content ...</Canvas>
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文