model {
      for (i in 1:n) {
        y[i] ~ dnorm(mu[i], 1 / (s1s2s3s4[ x[ i,1] , x[i,2] , x[i,3], x[i,4] ]) ^ 2)
        mu[i] <- a0 + a1[x[i,1]] + a2[ x[i,2] ] + a3[x[i,3]] + a4[x[i,4]] # Main effects
                        + a1a2[ x[i,1] , x[i,2] ] # Two-way effect (1x2)
                        + a1a3[ x[i,1] , x[i,3] ] # Two-way effect (1x3)
                        + a1a4[ x[i,1] , x[i,4] ] # Two-way effect (1x4)
                        + a2a3[ x[i,2] , x[i,3] ] # Two-way effect (2x3)
                        + a2a4[ x[i,2] , x[i,4] ] # Two-way effect (2x4)
                        + a3a4[ x[i,3] , x[i,4] ] # Two-way effect (3x4)
                        + a1a2a3[ x[ i,1] , x[i,2] , x[i,3] ] # Three-way effect (1x2x3)
                        + a1a2a4[ x[ i,1] , x[i,2] , x[i,4] ] # Three-way effect (1x2x4)
                        + a1a3a4[ x[ i,1] , x[i,3] , x[i,4] ] # Three-way effect (1x3x4)
                        + a2a3a4[ x[ i,2] , x[i,3] , x[i,4] ] # Three-way effect (2x3x4)
                        + a1a2a3a4[ x[ i,1] , x[i,2] , x[i,3] , x[i,4] ] # Four-way effect (1x2x3x4)
      }
      
      # Priors on sigma         
      for (j in 1:q.levels[1]) {
        for (k in 1:q.levels[2]) {
          for (l in 1:q.levels[3]) {
            for (m in 1:q.levels[4]) {
                sigma.frac[j,k,l,m] ~ dnorm(0.0, 1 / a1a2a3SD ^ 2)
                s1s2s3s4[j,k,l,m] <- max(sigma.frac[j,k,l,m], medianCellSD / 1000) # Prevent zero sigma.
            }
          }
        }
      }     

      # Baseline
      a0 ~ dnorm(yMean, 1 / (ySD * 5) ^ 2)
      
      # Main effect (1)    
      for (k in 1:q.levels[1]) {
        a1[k] ~ dnorm(0.0, 1 / a1SD ^ 2)
      }
      a1SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
      
      # Main effect (2)    
      for (k in 1:q.levels[2]) {
        a2[k] ~ dnorm(0.0, 1 / a2SD ^ 2)
      }
      a2SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
      
      # Main effect (3)
      for (k in 1:q.levels[3]) {
        a3[k] ~ dnorm(0.0, 1 / a3SD ^ 2)
      }
      a3SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
      
      # Main effect (4)
      for (k in 1:q.levels[4]) {
        a4[k] ~ dnorm(0.0, 1 / a4SD ^ 2)
      }
      a4SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
      
      # Two-way effect (1x2)
      for (k in 1:q.levels[1]) {
        for (l in 1:q.levels[2]) {
          a1a2[k,l] ~ dnorm(0.0, 1 / a1a2SD ^ 2)
        }
      }
      a1a2SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
      
      # Two-way effect (1x3)
      for (k in 1:q.levels[1]) {
        for (l in 1:q.levels[3]) {
          a1a3[k,l] ~ dnorm(0.0, 1 / a1a3SD ^ 2)
        }
      }
      a1a3SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
      
      # Two-way effect (1x4)
      for (k in 1:q.levels[1]) {
        for (l in 1:q.levels[4]) {
          a1a4[k,l] ~ dnorm(0.0, 1 / a1a4SD ^ 2)
        }
      }
      a1a4SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
      
      # Two-way effect (2x3)
      for (k in 1:q.levels[2]) {
        for (l in 1:q.levels[3]) {
          a2a3[k,l] ~ dnorm(0.0, 1 / a2a3SD ^ 2)
        }
      }
      a2a3SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])    
            
      # Two-way effect (2x4)
      for (k in 1:q.levels[2]) {
        for (l in 1:q.levels[4]) {
          a2a4[k,l] ~ dnorm(0.0, 1 / a2a4SD ^ 2)
        }
      }
      a2a4SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])  
       
      # Two-way effect (3x4)
      for (k in 1:q.levels[3]) {
        for (l in 1:q.levels[4]) {
          a3a4[k,l] ~ dnorm(0.0, 1 / a3a4SD ^ 2)
        }
      }
      a3a4SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])   
      
      # Three-way effect (1x2x3)
      for (k in 1:q.levels[1]) {
        for (l in 1:q.levels[2]) {
          for (m in 1:q.levels[3]) {
            a1a2a3[k,l,m] ~ dnorm(0.0, 1 / a1a2a3SD ^ 2)
          }
        }
      }
      a1a2a3SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
      
      # Three-way effect (1x2x4)
      for (k in 1:q.levels[1]) {
        for (l in 1:q.levels[2]) {
          for (m in 1:q.levels[4]) {
            a1a2a4[k,l,m] ~ dnorm(0.0, 1 / a1a2a4SD ^ 2)
          }
        }
      }
      a1a2a4SD ~ dgamma(aGammaShRa[1], aGammaShRa[2]) 

      # Three-way effect (1x3x4)
      for (k in 1:q.levels[1]) {
        for (l in 1:q.levels[3]) {
          for (m in 1:q.levels[4]) {
            a1a3a4[k,l,m] ~ dnorm(0.0, 1 / a1a3a4SD ^ 2)
          }
        }
      }
      a1a3a4SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
      
      # Three-way effect (2x3x4)
      for (k in 1:q.levels[2]) {
        for (l in 1:q.levels[3]) {
          for (m in 1:q.levels[4]) {
            a2a3a4[k,l,m] ~ dnorm(0.0, 1 / a2a3a4SD ^ 2)
          }
        }
      }
      a2a3a4SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])   
                               
      # Four-way effect (1x2x3x4)
      for (k in 1:q.levels[1]) {
        for (l in 1:q.levels[2]) {
          for (m in 1:q.levels[3]) {
            for (n in 1:q.levels[4]) {
              a1a2a3a4[k,l,m,n] ~ dnorm(0.0, 1 / a1a2a3a4SD ^ 2)
            }
          }
        }
      }
      a1a2a3a4SD ~ dgamma(aGammaShRa[1], aGammaShRa[2])
       
      # Means
      for (l in 1:q.levels[1]) {
        for (m in 1:q.levels[2]) {
          for (n in 1:q.levels[3]) {
            for (o in 1:q.levels[4]) {
              m1m2m3m4[l,m,n,o] <- a0 + a1[l] + a2[m]  + a3[n]  + a4[o]
                                      + a1a2[l,m]
                                      + a1a3[l,n]
                                      + a1a4[l,o]
                                      + a2a3[m,n]
                                      + a2a4[m,o]
                                      + a3a4[n,o]
                                      + a1a2a3[l,m,n]
                                      + a1a2a4[l,m,o]
                                      + a1a3a4[l,n,o]
                                      + a2a3a4[m,n,o]
                                      + a1a2a3a4[l,m,n,o]
            }
          }
        }
      }
      
      sigmaSh <- 1 + sigmaMode * sigmaRa
      sigmaRa <- (sigmaMode + sqrt(sigmaMode ^ 2 + 4 * sigmaSD ^ 2)) / (2 * sigmaSD ^ 2)
      sigmaMode ~ dgamma(sGammaShRa[1], sGammaShRa[2])
      sigmaSD ~ dgamma(sGammaShRa[1], sGammaShRa[2])
}