---
title: "Power Analysis for Two-level Longitudinal Models with Missing Data"
author: "Kristoffer Magnusson"
date: "`r Sys.Date()`"
output: rmarkdown::html_vignette
bibliography: citations.bib
vignette: >
  %\VignetteIndexEntry{Tutorial: Two-level Longitudinal Power Analysis}
  %\VignetteEngine{knitr::rmarkdown}
  %\VignetteEncoding{UTF-8}
---

```{r, echo=FALSE, warning=FALSE, message=FALSE}
library(powerlmm)
```


# Introduction
This vignette shows how to use the *powerlmm*-package to design a two-level longitudinal study. The package does not only contain tools to calculate power for these models, but also tools to help you understand 
the implications of the model's parameters. The real world performance of the study design can also be evaluated using Monte Carlo simulations (see the simulation vignette). The package also includes functions to help you understand the consequences of
ignoring clustering effects at the third level (see the three-level vignette). The design effect can be calculated, as well as the inflation of Type I errors when a random slope at the third level is ignored.

# Supported models
Currently power can be calculated for the following designs

* Two-level model (subjects with repeated measures)
* Nested three-level models (subjects with repeated measures, nested within e.g. therapists)
* Partially nested designs (only one treatment arm in the nested three-level models have clustering)
* **Random slopes**: It is possible to include random slopes at both the cluster and subject level. 
* **Unbalanced designs**: Unbalanced designs are supported; e.g. treatments can have different number of subjects and/or clusters. It is also possible to have unbalanced cluster sizes within a treatment. 
* **Missing data**: The power calculations can account for missing data, either by manually specifying the dropout per time point, or by using a Weibull survival function. 


# Two-level longitudinal linear mixed-effects model with random slopes
This is the typical longitudinal linear mixed model, which in multilevel notion is written as

$$
\begin{align}
\text{Level 1}& \notag\\\
Y_{ij} &= \beta_{0j} + \beta_{1j}t_{ij} + R_{ij}\\\
\text{Level 2}& \notag\\\
\beta_{0j} &= \gamma_{00} + \gamma_{01} TX_j + U_{0j} \\\
\beta_{1j} &= \gamma_{10} + \gamma_{11} TX_j + U_{1j} \\\
\end{align}
$$
with, 
$$
\begin{equation}
\begin{pmatrix}
U_{0j} \\\
 U_{1j}
\end{pmatrix}
\sim\mathcal{N}
\left(
\begin{matrix}
0 &\\\
0
\end{matrix}
,
\begin{matrix}
 \sigma_{u_0}^2 & \sigma_{u_{01}}\\\
 \sigma_{u_{01}} & \sigma_{u_1}^2
\end{matrix}
\right)
,
\end{equation}
$$
and
$$
\begin{equation}
R_{ij} \sim\mathcal{N}(0, ~\sigma_e^2)
\end{equation}
$$


All designs are setup using the `study_parameters` function. Parameters can be specified
either directly or by their standardized counterpart.

The arguments in `study_parameters` are

parameter        | `study_parameters()-`argument
---------------- | -----------
$\gamma_{00}$    | `fixed_intercept`
$\gamma_{01}$    | NA; assumed to be 0
$\gamma_{10}$    | `fixed_slope`
$\gamma_{11}$    | calculated from `effect_size`
$\sigma_{u_0}$      | `sigma_subject_intercept`
$\sigma_{u_1}$    | `sigma_subject_slope`
$\sigma_{u_{01}}$      | calculated from `cor_subject`
$\sigma_e$         | `sigma_error`

## Standardized and unstandardized formulation

For a two-level model power depends on `n1`, `n2`, the amount of baseline variance at the subject level (`icc_pre_subjects`) and the ratio of subject-level random slope variance to the within-subject error variance (`var_ratio`). 


Standardized        | Calculation
------------------- | -----------
`icc_pre_subjects`  | $\sigma_{u_0}^2/(\sigma_{u_0}^2 + \sigma_e^2)$  
`var_ratio`         | $\sigma_{u_1}^2/\sigma_e^2$  

### Effect sizes
The argument `effect_size` either accepts the raw difference between the groups at posttest, or a standardized effect size by passing the `cohend(...)` function. Cohen's *d* can be calculated using either the pretest, posttest, or random slope SD as the standardizer (denominator). See `?cohend` for options.


For standardized effect sizes that use either the pretest or posttest SD, the effect size refers to the standardized difference between the groups at posttest,
$$\delta_{101} = \frac{\text{ES} \times \sigma}{T_{end}}.$$
Where the standardizer $\sigma$ is one of the following standardizers (based either on the treatment or control groups variance components):

- pretest SD,
$$ \sigma_{pre} = \sqrt{\sigma_{u0}^2 + \sigma_{e}^2}.$$
- posttest SD,
$$ \sigma_{post} =  \sqrt{\sigma_{u0}^2 + 2T_{end}\sigma_{u01} + T_{end}^2\sigma_{u1}^2 + \sigma_{e}^2}.$$

If the random slope SD (cf. @Raudenbush_Xiao-Feng_2001) is used as the standardizer, the ES now indicate the difference per unit of time, 
$$\delta_{101} = \text{ES} \times \sigma_{u1}.$$


## Setting up the model using study_parameters()
Here's an example of specifying the "same" model using standardized or unstandardized inputs.

```{r}
p1 <- study_parameters(n1 = 11,
                      n2 = 25,
                      sigma_subject_intercept = 1.44,
                      sigma_subject_slope = 0.2,
                      sigma_error = 1.44,
                      effect_size = cohend(-0.5, 
                                           standardizer = "pretest_SD"))

p2 <- study_parameters(n1 = 11,
                      n2 = 25,
                      icc_pre_subject = 0.5,
                      var_ratio = 0.019,
                      effect_size = cohend(-0.5, 
                                           standardizer = "pretest_SD"))
p1
```

To calculate power we use `get_power`
```{r}
get_power(p2)
```

# Missing data
Missing data can be accounted for in the power calculations by the argument `dropout`. Intermittent missing
data is not currently supported, thus missing data is monotonically increasing. Two helper functions are used to define the dropout pattern; either `dropout_manual` or `dropout_weibull`. Here I will use `dropout_weibull`.

```{r}
p2 <- study_parameters(n1 = 11,
                      n2 = 25,
                      icc_pre_subject = 0.5,
                      var_ratio = 0.019,
                      dropout = dropout_weibull(proportion = 0.3, 
                                                rate = 1/2),
                      effect_size = cohend(-0.5, 
                                           standardizer = "pretest_SD"))
```

Here I've chosen to have a total of 30 % of the participant dropout during the study, with more dropout occurring earlier in the study period. We can plot the model and missing data pattern using `plot`.

```{r, fig.width=8}
plot(p2)
```

And the power can be calculated using `get_power`.
```{r, message = FALSE}
get_power(p2)
```
Not surprisingly, power is decreased compared to the model with no missing data.

## Different dropout patterns per treatment group
The helper function `per_treatment` allows some options to differ by treatment arm, here we will use it to specify a different dropout pattern in each treatment group.
```{r, fig.width=4}

d <- per_treatment(control = dropout_weibull(proportion = 0.3, 
                                                rate = 1/2),
                   treatment = dropout_weibull(proportion = 0.5, 
                                                rate = 2))

p2 <- study_parameters(n1 = 11,
                      n2 = 25,
                      icc_pre_subject = 0.5,
                      var_ratio = 0.019,
                      dropout = d,
                      effect_size = cohend(-0.5, 
                                           standardizer = "pretest_SD"))

plot(p2, type = "dropout")
```

## Different number of subjects per treatment group
The amount of subjects per treatment group can also be specified per treatment. Let's specify two studies
that both have a total of 60 participants. The first have equal allocation (30 per group), and the second unequal allocation.

```{r}
p1 <- study_parameters(n1 = 11,
                      n2 = 30,
                      icc_pre_subject = 0.5,
                      var_ratio = 0.019,
                      effect_size = cohend(-0.5, 
                                           standardizer = "pretest_SD"))
p2 <- study_parameters(n1 = 11,
                      n2 = per_treatment(control = 10,
                                         treatment = 50),
                      icc_pre_subject = 0.5,
                      var_ratio = 0.019,
                      effect_size = cohend(-0.5, 
                                           standardizer = "pretest_SD"))

p1
p2
```

If we calculate power we can see that balanced allocation is more powerful.
```{r}
get_power(p1)$power
get_power(p2)$power
```

# Power curves
Since power is influenced by many different parameters, the function `get_power_table` lets you compare the effect of up to 3 different parameters, and visualize the relationships. Let's see how the number of subjects and the variance ratio influences power. 
```{r}
p1 <- study_parameters(n1 = 11,
                      n2 = 30,
                      icc_pre_subject = 0.5,
                      var_ratio = 0.019,
                      effect_size = cohend(-0.5, 
                                           standardizer = "pretest_SD"))

x <- get_power_table(p1, n2 = seq(10, 30, by = 5), var_ratio = c(0.01, 0.02, 0.05))
x
```
```{r, fig.width = 5}
plot(x)
```

We see that the variance ratio influences power more than the number of subjects. 

# References
