0

我对 ActionScript 3 很陌生,我一直在尝试在类文件中执行以下操作。我试图在网上寻找解决方案,但找不到合适的答案,可能是因为我没有寻找正确的搜索词等。

无论如何,我正在尝试在 Adob​​e Animate CC 中的 FLA 文件“Campfire.FLA”中制作基本动画,其中在 Campfire 上按下鼠标会导致附着在悬浮棒上的一块煤炭发光,然后冷却松开鼠标按钮。在主时间线上,我可以很好地执行它,但我想将信息传输到类文件/文档文件中,但无济于事。

该代码是我在 FLA 的主时间轴第 1 帧上使用的代码,它在下面工作得非常好:

stop();
/* Instance names:
    Fire = Instance of "FireButton"; simplebutton.
    STween = Instance of "Stick Tween"; MovieClip, simple tween animation the object, "MarshmallowStick" moving.
    Stick = Instance of "Marshmallow Stick"; MovieClip.
    CoalRock = Instance of "Coal"; MovieClip.
*/
Fire.addEventListener(MouseEvent.MOUSE_DOWN, RockHot)
function RockHot(e: MouseEvent): void {
    stopPlayReverse();
    // Causes Coal and Stick to play their animation upon clicking Fire.
    STween.Stick.play();
    STween.Stick.CoalRock.play();

}
Fire.addEventListener(MouseEvent.MOUSE_UP, RockCold)
function RockCold(e: MouseEvent): void {
    STween.Stick.CoalRock.addEventListener(Event.ENTER_FRAME, playReverse, false, 0, true);
    STween.Stick.gotoAndPlay(1);
    // Upon letting go of mouse button, it causes the coal to cool down/ play reverse. Stick resets to Frame 1.

}
function playReverse(e: Event): void {
    if (STween.Stick.CoalRock.currentFrame == 1) {
        stopPlayReverse();
    // If Coal is back on Frame 1, it stops.
    } else {
        STween.Stick.CoalRock.prevFrame();
    // If Coal is not on Frame 1 it continues going reverse where it left off.
    }
}

function stopPlayReverse(): void {
    if (STween.Stick.CoalRock.hasEventListener(Event.ENTER_FRAME)) {
        STween.Stick.CoalRock.removeEventListener(Event.ENTER_FRAME, playReverse);
    // Stops the function playreverse()
    }
}

但是,在尝试将信息迁移到 ActionScript 文件时,我遇到了几个问题。首先,我尝试为上面的每个对象创建一个 ActionScript 3 类文件,其中大部分信息都是空白的,因为我不知道如何在它们之间通信事件处理程序。MovieClips 的大部分信息都没有信息,“MarshmallowStick”如下:

package  {

    import flash.display.MovieClip;


    public class MarshmallowStick extends MovieClip {


        public function MarshmallowStick() {
               // Empty, no constructor code.
        }
    }

}

对于“火”类文件,我尝试了类似的东西:

package {

    import flash.display.*;
    import flash.events.*;
    import Coal;


    public class FireButton extends SimpleButton {
        public var CoalRock = Coal;
        public function FireButton() {
        Coalrock = new Coal ();
        this.addEventListener(MouseEvent.CLICK, RockHot)
            function RockHot(e: MouseEvent): void {
                CoalRock.play();
                trace("OK");
                trace(CoalRock);
            }
        }
    }
}

然而,经测试发现,该文件似乎只是创建了一个名为 CoalRock 的新对象,与主舞台上的对象无关。因此,单击 FireButton 只会播放新对象。

我尝试在名为“Main.as”的文件中创建如下所示的文档类:

package {

    import flash.display.*;
    import flash.events.*;


    public class Main extends MovieClip {
        public var Fire: FireButton;
        public var CoalRock: Coal;
        public var Stick: MarshmallowStick;
        public var STween: StickTween;

        public function Main() {
            CoalRock = new Coal();
            Fire = new FireButton();
            Stick = new MarshmallowStick();
/*          
            addChild(Fire);
            addChild(CoalRock);
            addChild(Stick);
            addChild(STween);
*/
// RIP, well it's pretty much the same code as above. Just without the nested symbols/ objects.
            Fire.addEventListener(MouseEvent.MOUSE_DOWN, RockHot)
            function RockHot(e: MouseEvent): void {
                stopPlayReverse();
                //Eye + Emblem glow
                Stick.play();
                CoalRock.play();
                trace("OK");

            }
            Fire.addEventListener(MouseEvent.MOUSE_UP, RockCold)
            function RockCold(e: MouseEvent): void {
                CoalRock.addEventListener(Event.ENTER_FRAME, playReverse, false, 0, true);
                Stick.gotoAndPlay(1);
            }
            function playReverse(e: Event): void {
                if (CoalRock.currentFrame == 1) {
                    stopPlayReverse();
                } else {
                    CoalRock.prevFrame();
                }
            }

            function stopPlayReverse(): void {
                if (CoalRock.hasEventListener(Event.ENTER_FRAME)) {
                    CoalRock.removeEventListener(Event.ENTER_FRAME, playReverse);
                }
            }
        }
    }

}

addChild()但事实证明,据我测试,它只影响通过井添加的对象。但这样做的主要目的是让脚本影响主舞台/场景中已经存在的对象。

如果您想查看它的播放方式/假设播放方式,您可以获取主时间线代码并将其粘贴到 FLA 文件中,其中包含提供的实例。

我不知道 Stack 将如何格式化它。// 假设是多行注释。

4

1 回答 1

0

这是一个复杂的问题。

您(可能)最需要的是一些封建等级制度,以便对象倾向于他们自己和他们的直系子女,但不会更深,也不会完全向上:

  • Container→(接口方法)→Child→(倾向于拥有孩子)
  • 容器←(状态事件)←孩子

通常,孩子必须不知道其父母,并且应该与状态事件进行通信。通过这种方式,您可以将这样的孩子放入任何容器中,而不会出现该孩子可能会向上期待某些不存在的父结构的风险。

所以,你的问题。

首先。访问主时间线上已经存在的对象。好吧,唯一的技巧不是创建的,而是获取对现有的引用。

package
{
    // Imports.

    public class Main extends MovieClip
    {
        // If you have an instance of MarshmallowStick with the
        // instance name "Stick" on the main timeline,
        // you don't need to do anything else.
        //
        // Default publish settings are to auto-declare
        // the main timeline instance into the
        // appropriately named variable.

        public var Stick:MarshmallowStick;

PS自己从 Tween中找出Stick

第二。要访问 Stick 中的 Coal,您需要在对应的类中声明一个适当的变量。此外,将向前和向后播放事物所需的东西尽可能靠近它们操作的对象是很有意义的。

package
{
    import flash.events.Event;
    import flash.display.MovieClip;

    public class MarshmallowStick extends MovieClip
    {
        // You don't seem to need a separate class for Coal.
        // Having it as a regular MovieClip will suffice.
        public var Coal:MovieClip;

        // Call this to play animation forward.
        public function playNormal():void
        {
            removeEventListener(Event.ENTER_FRAME, onReverse);

            gotoAndPlay(1);
            Coal.play();
        }

        // Call this to play animation backward.
        public function playReverse():void
        {
            Coal.stop();
            gotoAndPlay(1);

            addEventListener(Event.ENTER_FRAME, onReverse);
        }

        // This method does not need to be seen from the outside
        // so declare it as private rather than public.
        private function onReverse(e:Event):void
        {
            if (Coal.currentFrame > 1)
            {
                Coal.prevFrame();
            }
            else
            {
                playNormal();
            }
        }

        // Call this to stop playing into any direction.
        public function stopPlaying():void
        {
            stop();
            Coal.stop();

            removeEventListener(Event.ENTER_FRAME, onReverse);
        }
    }
}

第三。避免在函数内部声明函数。您可以阅读什么是闭包以及如何在 AS3 中处理它们,但目前(可能在可预见的将来)您不需要它们。

package
{
    // Imports.

    public class Main extends MovieClip
    {
        public var Fire:SimpleButton;
        public var Stick:MarshmallowStick;

        public function Main()
        {
            Fire.addEventListener(MouseEvent.MOUSE_DOWN, makeHot);

            // The rest of the code.
        }

        function makeHot(e:MouseEvent):void
        {
            Stick.playNormal();
            trace("OK");
        }

第四。不要子类化按钮。创建一个简单的无类按钮并订阅其MouseEvent.CLICKMouseEvent.MOUSE_DOWN事件以在某个知道此按钮用途的地方处理所有必要的操作就足够了。我上面已经说过了。封建等级制度。按钮应该触发一个事件,然后它的持有者应该捕获该事件并做出反应。按钮本身不应该知道它在哪里或它的目的是什么,更不用说尝试做事了。

于 2020-05-11T03:06:12.373 回答