⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 toneplayer.java

📁 J2me唆哈的代码
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
                    if (sequence[i+1] < 2){
                        reportErr(9);
                    }
                    note = sequence[i+2];
                    if (!(note == SILENCE || note >= 0)){
                        reportErr(11);
                    }
                    break;
                   
                case SET_VOLUME:
                    if (sequence[i+1] < 0 || sequence[i+1] > 100){
                        reportErr(10);
                    }
                    len += 2;
                    break;
                    
                case PLAY_BLOCK:
                    if (blockEnds.get(new Integer(sequence[i+1])) == null){ 
                        reportErr(2);
                    }
                    tmp = ((Integer)(blockEnds.get(new Integer(sequence[i+1])))).intValue(); 
                    if (inBlock) {
                        thisBlockEnd += tmp;
                    } else {
                        len += tmp;
                    }
                    break;
        
                case VERSION:
                case TEMPO:
                case RESOLUTION:
                    reportErr(12);
                    break;
                default: 
                    // SILENCE or normal tone
                    if (inBlock) {
                        thisBlockEnd += 2;
                    } else {
                        len += 2;
                    }
                } // switch
            } // end of for(i)
            
            if (inBlock) {
                reportErr(1);
            }
            
            // valid tone seq
            toneSeq = new int[len];
    
            curTime = 0;
            p = 0;
    
            i = startseq;
            int mul = 1;
    
            while (i < sequence.length) {
                note =  sequence[i];
                switch (note) {
                case BLOCK_START: // blk definition, start
                    do {
                        i += 2;
                    } while (sequence[i] != BLOCK_END);
                    break;
                    
                case PLAY_BLOCK:  // play_blk
                    sp.push(new Integer(i+2));
                    i = ((Integer)blockStarts.get(new Integer(sequence[i+1]))).intValue() + 2;
                    continue;
        
                case BLOCK_END: // end playing blk
                    i = ((Integer)(sp.pop())).intValue();
                    continue;
        
                case SET_VOLUME:
                    // 0 <= sequence[i+1] <= 100
                    toneSeq[p++] = SET_VOLUME;
                    toneSeq[p++] = (sequence[i+1] & 0x7f);
                    
                    break;
                    
                case REPEAT:
                    // 2 <= sequence[i+1] <= 127
                    mul = sequence[i+1];
                    break;
        
                default: // regular tone or SILENCE
                    toneSeq[p++] = sequence[i];
                    // dur as milliseconds
                    toneSeq[p++] += (sequence[i+1]&0x7f) * mul * 240000 / frac;
                    curTime += toneSeq[p-1];
                    mul = 1;
                } // switch
                
                i += 2;
            } // while
        } catch (IllegalArgumentException ex) {
            throw ex;
        } catch (Exception ex) {
            throw new IllegalArgumentException(ex.getMessage());
        }
        seqChanged = true;
    }
    

    private void reportErr(int code) {
        throw new IllegalArgumentException("bad tone param: err code " + code);
    }

    /**
     * ==========================
     * Methods for VolumeControl.
     * =========================
     */
    /**
     * The worker method to actually obtain the control.
     *
     * @param vol the volume level to be set.  
     * @return the actual level has been set.
     */
    protected int  doSetLevel(int vol) {
        if(clip.isControlSupported(FloatControl.Type.VOLUME)){
            ((FloatControl)clip.getControl(FloatControl.Type.VOLUME)).setValue((float)vol/100);
            return vol;
        }else{
            if(clip.isControlSupported(BooleanControl.Type.MUTE)){
                if(vol<=0){
                    ((BooleanControl)clip.getControl(BooleanControl.Type.MUTE)).setValue(true);
                }else if(vol>0){
                    ((BooleanControl)clip.getControl(BooleanControl.Type.MUTE)).setValue(false);
                }
            }
            return (int)(clip.getLevel()*100);
        }
    }
    
    private void harmonics(int voices, double second, double third, double fourth, double fifth)
    {
        int k;

        double max = 0.0;

        for (k = 0; k < 361; ++k)
        {
            harmwave[k] =
                  (    1.0 * Math.sin (k *  2. * Math.PI / 360.) +
                    second * Math.sin (k *  4. * Math.PI / 360.) +
                     third * Math.sin (k *  6. * Math.PI / 360.) +
                    fourth * Math.sin (k *  8. * Math.PI / 360.) +
                     fifth * Math.sin (k * 10. * Math.PI / 360.) );
            if (harmwave[k] > max){
                max = harmwave[k];
            }else if (-harmwave[k] > max){
                max = -harmwave[k];
            }

            // for the milliwatt tone (single note!)
            //sinewave[k] = 0.707 * Math.sin (k *  2. * Math.PI / 360.);
        }
        // allow up to number_of_notes simultaneous notes with harmwave[]
        for (k = 0; k < 361; ++k){
            //harmwave[k] *= ((0.707/voices)/max);   // eg. 0.35 for 2 voices
            harmwave[k] *= ((0.707/voices)/max);
        }
    }
    
    private void test(){
        
        for (int tries = 0; tries < 2; ++tries)
        {
            // CAF: try a few, at different rates
            pcm = new AudioFormat(AudioFormat.Encoding.PCM_SIGNED,
                                  rate, sampleSizeInBits, channels, 
                                  frameSize, rate, bigendian);
            DataLine.Info info = new DataLine.Info(
                        Clip.class,
                        pcm);  // no buffer size -- will that be OK
            try
            {
                clip = (Clip) AudioSystem.getLine(info);
                
                //System.out.println("Audio DataLine started");

                // hack to work around JavaSound bug 4515126.
                byte [] sampleTest = new byte[2];
                sampleTest[0] = 0;
                sampleTest[1] = 1;
                clip.open(pcm, sampleTest, 0, sampleTest.length);
                clip.close();
                if (sampleTest[1] == 0) // byte swapping occured in JavaSound
                {
                    bigendian = ! bigendian;
                    System.out.println("Bigendian=" + bigendian + " (swapped after test)");
                    continue;  // try a second time
                }
                break;
            }
            catch (Exception ex)
            {
                System.out.println("Audio exception: " + ex);
                clip = null;
            }
        }
        
    }
    
    private void toneInitSeq(){
        
        test();
        int len=rate*curTime/1000;
        if(samples==null||samples.length<(len<<1)){
            samples=null;
            samples=new byte[len<<1];
        }
        len=0;
        for(int i=0; i<toneSeq.length; i+=2){

            int lgt=rate*toneSeq[i+1]/1000;
            double volt=0;
            double deg;
            double degm;
            int degi;
            for(int j=0; j<lgt; ++j){
               
                if(toneSeq[i]>0){
                    deg = ((toneSeq[i]/127.0)*80+80) * j;
                    degi = (int) deg;
                    degm = deg - (double)degi;

                    /*
                     volt += sinewave[degi%360] +  // linear interpolate
                            degm * (sinewave[(degi%360)+1] - sinewave[degi%360]);
                     */

                    volt += harmwave[degi%360] +  // linear interpolate
                        degm * (harmwave[(degi%360)+1] - harmwave[degi%360]);
                    
                    short val = (short)(volt * 32767.);
                    
                    if(bigendian){
                        samples[len+(j<<1)]=(byte)(val>>8);
                        samples[len+(j<<1)+1]=(byte)(val&0xff);
                    }else{
                        samples[len+(j<<1)+1]=(byte)(val>>8);
                        samples[len+(j<<1)]=(byte)(val&0xff);
                    }
                }else{
                    samples[len+(j<<1)]=0;
                    samples[len+(j<<1)+1]=0;
                }
            }
            len+=(lgt<<1);
        }
        try{
            ByteArrayInputStream bis=new ByteArrayInputStream(samples);
            AudioInputStream ais=new AudioInputStream(bis,pcm,samples.length/(sampleSizeInBits>>3));
            clip.open(ais);
        }catch(Exception e){
            e.printStackTrace();
        }
    }
    
    public void run(){
        try{
         
            if(clip!=null&&clip.isOpen()){
                clip.start();
                while (clip.isActive() && thread != null) {
                    try {
                        Thread.sleep(300);
                    }catch (Exception e) {
                        break;
                    }
                }
                this.sendEvent(PlayerListener.END_OF_MEDIA,null);
            }
            if(thread!=null){
                thread.interrupt();
                thread=null;
            }
        }catch(Exception e){
            e.printStackTrace();
        }
    }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -