2015-06-16 14 views
6

È necessario creare un visualizzatore del livello audio con un motivo personalizzato. Ho l'immagine impostata come PNG. mio approccio attuale è come questoAnimazione UIImmagine basata sul feedback del livello del volume

1) Ottenere il livello audio del microfono

2) Caricare l'immagine rilevante per l'UIImageView in base al livello di volume.

// audio level timer 
self.levelTimer = [NSTimer scheduledTimerWithTimeInterval: 0.001 target: self selector: @selector(levelTimerCallback:) userInfo: nil repeats: YES]; 

ImageView

- (void)levelTimerCallback:(NSTimer *)timer { 
[self.audioRecorder updateMeters]; 
const double ALPHA = 0.05; 
double peakPowerForChannel = pow(10, (0.05 * [self.audioRecorder peakPowerForChannel:0])); 
lowPassResults = ALPHA * peakPowerForChannel + (1.0 - ALPHA) * lowPassResults; 

//NSLog(@"Average input: %f Peak input: %f Low pass results: %f", [self.audioRecorder averagePowerForChannel:0], [self.audioRecorder peakPowerForChannel:0], lowPassResults); 

if (lowPassResults > 0.0 && lowPassResults <= 0.05){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim1"]; 
} 
if (lowPassResults > 0.06 && lowPassResults <= 0.10){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim2"]; 
} 
if (lowPassResults > 0.11 && lowPassResults <= 0.15){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim3"]; 
} 
if (lowPassResults > 0.16 && lowPassResults <= 0.20){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim4"]; 
} 
if (lowPassResults > 0.21 && lowPassResults <= 0.25){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim5"]; 
} 
if (lowPassResults > 0.26 && lowPassResults <= 0.30){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim6"]; 
} 
if (lowPassResults > 0.31 && lowPassResults <= 0.35){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim7"]; 
} 
if (lowPassResults > 0.36 && lowPassResults <= 0.40){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim8"]; 
} 
if (lowPassResults > 0.41 && lowPassResults <= 0.45){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim9"]; 
} 
if (lowPassResults > 0.46 && lowPassResults <= 0.50){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim10"]; 
} 
if (lowPassResults > 0.51 && lowPassResults <= 0.55){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim11"]; 
} 
if (lowPassResults > 0.56 && lowPassResults <= 0.60){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim12"]; 
} 
if (lowPassResults > 0.61 && lowPassResults <= 0.65){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim13"]; 
} 
if (lowPassResults > 0.66 && lowPassResults <= 0.70){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim14"]; 
} 
if (lowPassResults > 0.71 && lowPassResults <= 0.75){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim15"]; 
} 
if (lowPassResults > 0.76 && lowPassResults <= 0.80){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim16"]; 
} 
if (lowPassResults > 0.81 && lowPassResults <= 0.85){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim17"]; 
} 
if (lowPassResults > 0.86 && lowPassResults <= 0.90){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim18"]; 
} 
if (lowPassResults > 0.86){ 
    imgViewRecordAnimation.image = nil; 
    imgViewRecordAnimation.image = [UIImage imageNamed:@"anim19"]; 
} 

} 

Ma l'uscita non è liscia come una vera e propria animazione visualizzatore. Quale dovrebbe essere l'approccio migliore? Condividi c'è qualche modo migliore per farlo.

Coppia di immagini

enter image description here

enter image description here

enter image description here

+0

Sembra che potrebbe essere lo stesso di questo problema: http://stackoverflow.com/questions/2834573/how-to-animate-the-change-of-image-in-an-uiimageview – dudeman

+0

Perché sei impostazione dell'immagine a zero ogni volta prima di impostare la proprietà dell'immagine ('imgViewRecordAnimation.image = nil;')? – arturdev

risposta

3

Se si sente l'immagine cambia sta cercando a scatti, si applica meglio le animazioni su di loro. A proposito, non è necessario impostare nil su imgViewRecordAnimation.image, poiché si stanno impostando le immagini corrette dopo tutte queste volte, il che introdurrà un ritardo non necessario. Puoi anche eseguire tutte le istruzioni if ​​in else, altrimenti ogni volta vengono eseguite tutte le istruzioni if.

Venendo alla soluzione, puoi semplicemente seguire il link che @MileAtNobel ha pubblicato. O se non vuoi fare molte modifiche al codice, puoi applicare una semplice animazione sulla proprietà backgroundColor. Puoi anche rimuovere il timer, controllare il codice sottostante e vedere se il codice funziona correttamente. Ho anche provato a ottimizzare il codice con una stretta somiglianza, spero che questo migliori le prestazioni.

BOOL flagToContinue ; //assign NO to this flag to stop updating the images 

-(void)levelTimerCallback 
{ 
    NSLog(@"Volume Logic Begins") ;//Volume level logic begins 
    [self.audioRecorder updateMeters]; 
    const double ALPHA = 0.05; 
    double peakPowerForChannel = pow(10, (0.05 * [self.audioRecorder peakPowerForChannel:0])); 
    lowPassResults = ALPHA * peakPowerForChannel + (1.0 - ALPHA) * lowPassResults ; 
    NSLog(@"Volume Logic ends") ;//Volume level logic ends 

    [UIView animateWithDuration:0.001f 
       delay:0.0f 
      options: UIViewAnimationOptionCurveLinear 
     animations:^{ 
      mgViewRecordAnimation.backgroundColor = [UIColor colorWithPatternImage:[NSString stringWithFormat:@"anim%d", (int)ceil(lowPassResults * 20)]]; 
     } 
     completion:^(BOOL finished) { 
      if(finished && flagToContinue) [self levelTimerCallback]; 
    }]; 
} 
+0

Grazie per la risposta, ma sempre uguale, non liscia come l'animazione normale delle immagini – sajaz

+0

In tal caso, dovresti vedere quanto tempo impiega per trovare il volume. Prendi i timestamp prima di iniziare e dopo aver terminato (come menzionato nel mio codice) e vedere la differenza di orario, penso che la tua logica del volume richieda più tempo, ecco perché le animazioni non sono fluide. – Trident

2

Ok, non ti darò una soluzione diretta, ma proverò a suggerire una soluzione, che dovrai provare. Quindi, anziché modificare l'immagine di imageView, scrivere un controllo personalizzato. Creare una sottoclasse di una vista. Sostituisci il metodo drawrect. In questo modo, è possibile disegnare il modello richiesto in base al valore di controllo o disegnare l'immagine stessa. Ma il primo approccio è raccomandato. Il disegno personalizzato è omogeneo rispetto alla modifica dell'immagine. Provalo e fammi sapere che funziona.

Problemi correlati