TypeError 1009 и отключение звука в AS3

Я действительно новичок в этом, поэтому мне очень жаль, если есть какое-то очевидное решение, которое я как-то упустил, ну да ладно...
Я нахожусь в процессе создания игры, и я пытался сделать меню выбора персонажа. У каждого персонажа будет уникальная версия одной и той же песни (с одинаковыми битами в секунду), поэтому, когда вы "наводите курсор" на один из вариантов, будет воспроизводиться песня персонажа, а остальные будут отключены (не приостановлены или не остановлены, поэтому как не потерять синхронизацию между всеми версиями песни)...
Прямо сейчас я пытался запрограммировать это только для одной из песен, а затем повторить метод для остальных, как только я это выясню.
Так...
Что я делаю неправильно?

Вот код:

package {

import flash.display.MovieClip;
import flash.events.Event; 
import flash.media.SoundTransform;
import flash.media.Sound;
import flash.media.SoundChannel; 
import flash.media.SoundMixer; 

public class MainThing extends MovieClip {
    private var soulcounting: Number = 1;
    private var Muting: Boolean = false;
    private var snd:Sound = new Sound();

    public function MainThing() {
        snd.load(new URLRequest("SOUL1.mp3"));
        stage.addEventListener(Event.ENTER_FRAME, FrameHandler);
        }

    private function FrameHandler(event: Event): void {
        if (Object(root).currentFrame == 2) {
            var channel:SoundChannel = snd.play(0,1);
            channel.soundTransform = new SoundTransform(1,0);
            /*the soulcounting number is determined by a keyboard function...  
            I didn't deem it necessary to be included in here,  
            as I don't think it is part of the problem.*/
            if (soulcounting == 1) {
                Object(root).SOULS.gotoAndStop(1);
                Muting = false;
                }

            if (soulcounting == 2) {
                Object(root).SOULS.gotoAndStop(2);
                Muting = true;
                }

            if (soulcounting == 3) {
                Object(root).SOULS.gotoAndStop(3);
                Muting = true;
                }

            if (soulcounting == 4) {
                Object(root).SOULS.gotoAndStop(4);
                Muting = true;
                }

            if (soulcounting == 5) {
                Object(root).SOULS.gotoAndStop(5);
                Muting = true;
                }

            if (soulcounting == 6) {
                Object(root).SOULS.gotoAndStop(6);
                Muting = true;
                }

            if(Muting){
                setVolume(channel);
                }

            if(!Muting){
                setVolume(channel, 1);
                }
            } 

    private function setVolume (Soundchannel:SoundChannel, volume:Number=0) {
        var trans:SoundTransform = Soundchannel.soundTransform;
        trans.volume = volume;
        Soundchannel.soundTransform = trans;
        }
    }
}

(Если я пытаюсь предварительно просмотреть swf, все работает нормально, пока я не получу второй кадр, в котором выходные данные начинают повторяться. TypeError: Ошибка #1009: не удается получить доступ к свойству или методу пустой ссылки на объект. At MainThing / FrameHandler ())
Ошибка типа # 1009, по-видимому, является очень распространенной ошибкой, но то, что я прочитал, не помогло мне с этой проблемой... Извините, если здесь уже было решение, и я просто не нашел достаточно..,
Заранее спасибо!

2 ответа

Пожалуйста, запустите ваш SWF в режиме отладки и укажите номер строки, которая вызывает ошибку. Не знаю, в чем причина проблемы, и не уверен, что ты хочешь делать, но почему ты так повторяешься? Это даже трудно читать. Точно то же самое, что вы можете сделать так:

public class MainThing extends MovieClip {
    private var soulcounting: Number = 1;
    private var Muting: Boolean = false;
    private var snd:Sound = new Sound();

    public function MainThing() {
        snd.load(new URLRequest("SOUL1.mp3"));
        stage.addEventListener(Event.ENTER_FRAME, FrameHandler);
    }

    private function FrameHandler(event: Event): void {
        if (Object(root).currentFrame != 2) return;
        var channel:SoundChannel = snd.play(0,1);
        channel.soundTransform = new SoundTransform(1,0);
        /*the soulcounting number is determined by a keyboard function...  
        I didn't deem it necessary to be included in here,  
        as I don't think it is part of the problem.*/
        SOULS.gotoAndStop(soulcounting);
        Muting = soulcounting != 1;
        setVolume(channel, Number(!Muting));
    } 

    private function setVolume (sch:SoundChannel, volume:Number=0) {
        var trans:SoundTransform = sch.soundTransform;
        trans.volume = volume;
        sch.soundTransform = trans;
    }

}

И это было бы еще эффективнее.

Спасибо Павлу Аудионису и VC.One за помощь в решении моей проблемы. Я решил это! Вместо использования SoundTransform.volume функция, я использовал SoundChannel.position и переменная для "сохранения" позиции, в которой предыдущая песня остановилась, так что следующая будет начинаться с этой точки: вот код, если кому-то интересно:

package {
import flash.display.MovieClip;
import flash.events.Event;
import flash.events.KeyboardEvent;
import flash.ui.Keyboard;
import flash.media.SoundTransform;
import flash.media.Sound;
import flash.media.SoundChannel; 
import flash.media.SoundMixer; 
import flash.net.URLLoader;
import flash.net.URLRequest;

public class MainThing extends MovieClip {
    private var bool:Boolean = false;
    private var snd1:Sound = new Sound();
    private var snd2:Sound = new Sound();
    private var snd3:Sound = new Sound();
    private var snd4:Sound = new Sound();
    private var snd5:Sound = new Sound();
    private var snd6:Sound = new Sound();
    private var channel1:SoundChannel = new SoundChannel();
    private var channel2:SoundChannel = new SoundChannel();
    private var channel3:SoundChannel = new SoundChannel();
    private var channel4:SoundChannel = new SoundChannel();
    private var channel5:SoundChannel = new SoundChannel();
    private var channel6:SoundChannel = new SoundChannel();
    private var songtime:Number = 0;
    private var NoSongHasBeenPlayedYet:Boolean = true;
    private var comesfromnothing:Boolean = true;
    private var comesfrom1:Boolean = false;
    private var comesfrom2:Boolean = false;
    private var comesfrom3:Boolean = false;
    private var comesfrom4:Boolean = false;
    private var comesfrom5:Boolean = false;
    private var comesfrom6:Boolean = false;

    public function MainThing() {
        snd1.load(new URLRequest("SOUL1.mp3"));
        snd2.load(new URLRequest("SOUL2.mp3"));
        snd3.load(new URLRequest("SOUL3.mp3"));
        snd4.load(new URLRequest("SOUL4.mp3"));
        snd5.load(new URLRequest("SOUL5.mp3"));
        snd6.load(new URLRequest("SOUL6.mp3"));
        stage.addEventListener(KeyboardEvent.KEY_DOWN, MenuButtons);

        stage.addEventListener(Event.ENTER_FRAME, FrameHandler);
    }
    private function FrameHandler(event: Event): void {
        if (Object(root).currentFrame == 2) {
            //I ommitted the part of the changes to the MovieClip's frames
            //the music function is called here... It didn't work anywhere else.
            Music();
            }
        } 
    private function Music():void{
        if(NoSongHasBeenPlayedYet){
            //this part happens either when the frame has just changed, or when the "songtime" variable has surpassed the audio length.
            comesfromnothing = true;
            channel1 = snd1.play(0,100);
            channel2 = snd2.play(0,100);
            channel3 = snd3.play(0,100);
            channel4 = snd4.play(0,100);
            channel5 = snd5.play(0,100);
            channel6 = snd6.play(0,100);
            NoSongHasBeenPlayedYet = false;
            bool = false;

            }
        if(!bool && songtime < 15150){
            switch(soulcounting){
                //In the original, there are 6 cases, for each song. I didn't put all of them in here because they are mostly the same, just with different numbers.
                case 1:
                    if(comesfromnothing){
                        trace(songtime);
                        songtime = channel2.position;
                        channel1.stop();
                        channel2.stop();
                        channel3.stop();
                        channel4.stop();
                        channel5.stop();
                        channel6.stop();
                        channel1 = snd1.play(songtime,100);
                        songtime = channel1.position;   
                        //the bool variable is there so that it doesn't create a new SoundChannel at every frame    
                        bool = true;
                        comesfromnothing = false;
                        comesfrom1 = true;

                    }
                    if(comesfrom2){
                        trace(songtime);
                        songtime = channel2.position;
                        channel1.stop();
                        channel2.stop();
                        channel1 = snd1.play(songtime,100);
                        songtime = channel1.position;       
                        bool = true;
                        comesfrom1 = true;
                        comesfrom2 = false;

                    }
                    if(comesfrom3){
                        trace(songtime);
                        songtime = channel3.position;
                        channel1.stop();
                        channel3.stop();
                        channel1 = snd1.play(songtime,100);
                        songtime = channel1.position;       
                        bool = true;
                        comesfrom1 = true;
                        comesfrom3 = false;
                    }
                    if(comesfrom4){
                        trace(songtime);
                        songtime = channel4.position;
                        channel1.stop();
                        channel4.stop();
                        channel1 = snd1.play(songtime,100);
                        songtime = channel1.position;       
                        bool = true;
                        comesfrom1 = true;
                        comesfrom3 = false;
                    }
                break;
            if(channel1.position  > 15100){
                trace(songtime);
                songtime = 0;
                channel1.stop();
                channel2.stop();
                channel3.stop();
                channel4.stop();
                channel5.stop();
                channel6.stop();
                NoSongHasBeenPlayedYet = true;

            }
        }
        public function MenuButtons(event: KeyboardEvent): void {
            if (Object(root).currentFrame == 2) {

            //this is the part of the controls, the bool is set to false so each time you press a botton, the audio can change.
            if (Keyboard.LEFT == event.keyCode && soulcounting != 1 && soulcounting != 4 && !Keyboardpressed) {
                soulcounting -= 1;
                bool = false;
                Keyboardpressed = true;} 
            else if (Keyboard.LEFT == event.keyCode && (soulcounting == 1 || soulcounting == 4) && !Keyboardpressed) {
                soulcounting += 2;
                bool = false;
                Keyboardpressed = true;} 
            else if (Keyboard.RIGHT == event.keyCode && soulcounting != 3 && soulcounting != 6 && !Keyboardpressed) {
                soulcounting += 1;
                bool = false;
                Keyboardpressed = true;} 
            else if (Keyboard.RIGHT == event.keyCode && (soulcounting == 3 || soulcounting == 6) && !Keyboardpressed) {
                soulcounting -= 2;
                bool = false;
                Keyboardpressed = true;} 
            else if ((Keyboard.UP == event.keyCode || Keyboard.DOWN == event.keyCode) && soulcounting > 3 && !Keyboardpressed) {
                soulcounting -= 3;
                bool = false;
                Keyboardpressed = true;} 
            else if ((Keyboard.DOWN == event.keyCode || Keyboard.UP == event.keyCode) && soulcounting < 4 && !Keyboardpressed) {
                soulcounting += 3;
                bool = false;
                Keyboardpressed = true;
                }
            }
        }
    }
Другие вопросы по тегам