enabling denorm pitch only at low bit-rate
authorJean-Marc Valin <jean-marc.valin@usherbrooke.ca>
Wed, 16 Sep 2009 11:57:17 +0000 (07:57 -0400)
committerJean-Marc Valin <jean-marc.valin@usherbrooke.ca>
Wed, 16 Sep 2009 11:57:17 +0000 (07:57 -0400)
libcelt/bands.c
libcelt/bands.h
libcelt/celt.c

index 4aafdc2..ccf191f 100644 (file)
@@ -216,7 +216,7 @@ void denormalise_bands(const CELTMode *m, const celt_norm_t * restrict X, celt_s
    }
 }
 
-int compute_new_pitch(const CELTMode *m, const celt_sig_t *X, const celt_sig_t *P, int *gain_id)
+int compute_new_pitch(const CELTMode *m, const celt_sig_t *X, const celt_sig_t *P, int norm_rate, int *gain_id)
 {
    int j ;
    celt_word16_t g;
@@ -248,22 +248,31 @@ int compute_new_pitch(const CELTMode *m, const celt_sig_t *X, const celt_sig_t *
 #ifdef FIXED_POINT
    {
       celt_word32_t num, den;
+      celt_word16_t fact;
+      fact = MULT16_16(QCONST16(.04, 14), norm_rate);
+      if (fact < QCONST16(1., 14))
+         fact = QCONST16(1., 14);
       num = Sxy;
       den = EPSILON+Sxx+MULT16_32_Q15(QCONST16(.03,15),Syy);
       shift = celt_ilog2(Sxy)-16;
       if (shift < 0)
          shift = 0;
       g = DIV32(SHL32(SHR32(num,shift),14),SHR32(den,shift));
-      if (Sxy < SHR32(MULT16_16(celt_sqrt(EPSILON+Sxx),celt_sqrt(EPSILON+Syy)),1))
+      if (Sxy < MULT16_32_Q15(fact, MULT16_16(celt_sqrt(EPSILON+Sxx),celt_sqrt(EPSILON+Syy))))
          g = 0;
       /* This MUST round down */
       *gain_id = EXTRACT16(SHR32(MULT16_16(20,(g-QCONST16(.5,14))),14));
    }
 #else
-   g = Sxy/(.1+Sxx+.03*Syy);
-   if (Sxy < .5*celt_sqrt(.1+Sxx*Syy))
-      g = 0;
-   *gain_id = floor(20*(g-.5));
+   {
+      float fact = .04*norm_rate;
+      if (fact < 1)
+         fact = 1;
+      g = Sxy/(.1+Sxx+.03*Syy);
+      if (Sxy < .5*fact*celt_sqrt(1+Sxx*Syy))
+         g = 0;
+      *gain_id = floor(20*(g-.5));
+   }
 #endif
    if (*gain_id < 0)
    {
index d47ecbd..6012be1 100644 (file)
@@ -64,7 +64,7 @@ void renormalise_bands(const CELTMode *m, celt_norm_t * restrict X);
  */
 void denormalise_bands(const CELTMode *m, const celt_norm_t * restrict X, celt_sig_t * restrict freq, const celt_ener_t *bands);
 
-int compute_new_pitch(const CELTMode *m, const celt_sig_t *X, const celt_sig_t *P, int *gain_id);
+int compute_new_pitch(const CELTMode *m, const celt_sig_t *X, const celt_sig_t *P, int norm_rate, int *gain_id);
 
 void apply_new_pitch(const CELTMode *m, celt_sig_t *X, const celt_sig_t *P, int gain_id, int pred);
 
index 50dad62..6dc3a34 100644 (file)
@@ -523,6 +523,7 @@ int celt_encode_float(CELTEncoder * restrict st, const celt_sig_t * pcm, celt_si
    int mdct_weight_shift = 0;
    int mdct_weight_pos=0;
    int gain_id=0;
+   int norm_rate;
    SAVE_STACK;
 
    if (check_encoder(st) != CELT_OK)
@@ -659,15 +660,13 @@ int celt_encode_float(CELTEncoder * restrict st, const celt_sig_t * pcm, celt_si
 #endif
    }
 
-   compute_band_energies(st->mode, freq, bandE);
-   for (i=0;i<st->mode->nbEBands*C;i++)
-      bandLogE[i] = amp2Log(bandE[i]);
-
+   norm_rate = (nbCompressedBytes-5)*8*(celt_uint32_t)st->mode->Fs/(C*N)>>10;
    /* Pitch analysis: we do it early to save on the peak stack space */
    /* Don't use pitch if there isn't enough data available yet, 
       or if we're using shortBlocks */
    has_pitch = st->pitch_enabled && st->pitch_permitted && (N <= 512) 
-            && (st->pitch_available >= MAX_PERIOD) && (!shortBlocks);
+            && (st->pitch_available >= MAX_PERIOD) && (!shortBlocks)
+            && norm_rate < 50;
    if (has_pitch)
    {
       find_spectral_pitch(st->mode, st->mode->fft, &st->mode->psy, in, st->out_mem, st->mode->window, NULL, 2*N-2*N4, MAX_PERIOD-(2*N-2*N4), &pitch_index);
@@ -682,8 +681,9 @@ int celt_encode_float(CELTEncoder * restrict st, const celt_sig_t * pcm, celt_si
    ALLOC(pitch_freq, C*N, celt_sig_t); /**< Interleaved signal MDCTs */
    if (has_pitch)
    {
+      
       compute_mdcts(st->mode, 0, st->out_mem+pitch_index*C, pitch_freq);
-      has_pitch = compute_new_pitch(st->mode, freq, pitch_freq, &gain_id);
+      has_pitch = compute_new_pitch(st->mode, freq, pitch_freq, norm_rate, &gain_id);
    }
    
    if (has_pitch)