# ================================================================
# BIOSTATISTIKA INTERMEDIATE
# REPEATED MEASURE ANALYSIS DENGAN R
# NAMA : IMAM FATHONI
# NIM  : 261018020
# Data simulasi berdasarkan Sun et al. (2026), Journal of Medical Internet Research
# 3 treatment x 3 repeated measurements
# Outcome: MVPA (minutes/week)
# ================================================================

# install.packages(c("tidyverse","afex","emmeans","rstatix","car",
#                    "effectsize","lme4","lmerTest","performance","ggpubr"))
suppressPackageStartupMessages({
  library(dplyr); library(tidyr); library(ggplot2); library(afex)
  library(emmeans); library(rstatix); library(car); library(effectsize)
  library(lme4); library(lmerTest); library(performance); library(ggpubr)
})
options(contrasts=c("contr.sum","contr.poly"))
afex_options(emmeans_model="multivariate")
theme_set(theme_bw(base_size=12))

# 1. DATA
dat_wide <- read.csv("FINAL_BLEND_MVPA_Data.csv")
dat_wide$treatment <- factor(dat_wide$treatment,
  levels=c("Control","Web-based","Blended"))
dat_wide$id <- factor(dat_wide$id)

dat_long <- dat_wide |>
  pivot_longer(c(mvpa_baseline,mvpa_12w,mvpa_24w),
               names_to="time",values_to="mvpa") |>
  mutate(time=factor(time,
    levels=c("mvpa_baseline","mvpa_12w","mvpa_24w"),
    labels=c("Baseline","12 weeks","24 weeks")))

# 2. EKSPLORASI
desk <- dat_long |> group_by(treatment,time) |>
  get_summary_stats(mvpa,type="mean_sd")
print(desk)
## # A tibble: 9 × 6
##   treatment time     variable     n  mean    sd
##   <fct>     <fct>    <fct>    <dbl> <dbl> <dbl>
## 1 Control   Baseline mvpa        30  159.  35.5
## 2 Control   12 weeks mvpa        30  184.  39.1
## 3 Control   24 weeks mvpa        30  195.  41.6
## 4 Web-based Baseline mvpa        30  163.  45.5
## 5 Web-based 12 weeks mvpa        30  186.  42.3
## 6 Web-based 24 weeks mvpa        30  198.  39.1
## 7 Blended   Baseline mvpa        30  163.  32.0
## 8 Blended   12 weeks mvpa        30  245.  33.8
## 9 Blended   24 weeks mvpa        30  268   33.5
ggplot(dat_long,aes(time,mvpa,colour=treatment,group=treatment))+
  stat_summary(fun=mean,geom="line",linewidth=1)+
  stat_summary(fun=mean,geom="point",size=2.5)+
  labs(y="MVPA (min/week)",x="Time")

ggplot(dat_long,aes(time,mvpa,group=id,colour=treatment))+
  geom_line(alpha=.18)+facet_wrap(~treatment)+
  stat_summary(aes(group=treatment),fun=mean,geom="line",linewidth=1.2)

# 3. REPEATED MEASURE ANOVA SATU ARAH: Blended
d1 <- droplevels(filter(dat_long,treatment=="Blended"))
d1 |> group_by(time) |> shapiro_test(mvpa)
## # A tibble: 3 × 4
##   time     variable statistic     p
##   <fct>    <chr>        <dbl> <dbl>
## 1 Baseline mvpa         0.974 0.648
## 2 12 weeks mvpa         0.950 0.170
## 3 24 weeks mvpa         0.956 0.240
aov1_rs <- anova_test(data=d1,dv=mvpa,wid=id,within=time,effect.size="pes")
aov1_rs
## ANOVA Table (type III tests)
## 
## $ANOVA
##   Effect DFn DFd       F        p p<.05  pes
## 1   time   2  58 334.176 1.47e-32     * 0.92
## 
## $`Mauchly's Test for Sphericity`
##   Effect     W     p p<.05
## 1   time 0.955 0.524      
## 
## $`Sphericity Corrections`
##   Effect   GGe     DF[GG]    p[GG] p[GG]<.05   HFe      DF[HF]    p[HF]
## 1   time 0.957 1.91, 55.5 2.94e-31         * 1.023 2.05, 59.32 1.47e-32
##   p[HF]<.05
## 1         *
get_anova_table(aov1_rs,correction="auto")
## ANOVA Table (type III tests)
## 
##   Effect DFn DFd       F        p p<.05  pes
## 1   time   2  58 334.176 1.47e-32     * 0.92
aov1 <- aov_ez(id="id",dv="mvpa",data=d1,within="time",
               anova_table=list(es=c("ges","pes"),correction="GG"))
summary(aov1)
## Warning in summary.Anova.mlm(object$Anova, multivariate = FALSE): HF eps > 1
## treated as 1
## 
## Univariate Type III Repeated-Measures ANOVA Assuming Sphericity
## 
##              Sum Sq num Df Error SS den Df F value    Pr(>F)    
## (Intercept) 4569354      1    79662     29 1663.43 < 2.2e-16 ***
## time         181912      2    15786     58  334.18 < 2.2e-16 ***
## ---
## Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
## 
## 
## Mauchly Tests for Sphericity
## 
##      Test statistic p-value
## time        0.95486 0.52381
## 
## 
## Greenhouse-Geisser and Huynh-Feldt Corrections
##  for Departure from Sphericity
## 
##       GG eps Pr(>F[GG])    
## time 0.95681  < 2.2e-16 ***
## ---
## Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
## 
##        HF eps   Pr(>F[HF])
## time 1.022815 1.466062e-32
em1 <- emmeans(aov1,~time)
pairs(em1,adjust="holm")
##  contrast              estimate   SE df t.ratio p.value
##  Baseline - X12.weeks     -81.6 4.09 29 -19.945 <0.0001
##  Baseline - X24.weeks    -104.8 3.97 29 -26.431 <0.0001
##  X12.weeks - X24.weeks    -23.2 4.69 29  -4.951 <0.0001
## 
## P value adjustment: holm method for 3 tests
friedman_test(d1,mvpa~time|id)
## # A tibble: 1 × 6
##   .y.       n statistic    df        p method       
## * <chr> <int>     <dbl> <dbl>    <dbl> <chr>        
## 1 mvpa     30      49.3     2 2.00e-11 Friedman test
# 4. MIXED DESIGN ANOVA: treatment x time
dat_long |> group_by(treatment,time) |> shapiro_test(mvpa)
## # A tibble: 9 × 5
##   treatment time     variable statistic     p
##   <fct>     <fct>    <chr>        <dbl> <dbl>
## 1 Control   Baseline mvpa         0.972 0.583
## 2 Control   12 weeks mvpa         0.975 0.694
## 3 Control   24 weeks mvpa         0.967 0.459
## 4 Web-based Baseline mvpa         0.966 0.425
## 5 Web-based 12 weeks mvpa         0.959 0.298
## 6 Web-based 24 weeks mvpa         0.977 0.734
## 7 Blended   Baseline mvpa         0.974 0.648
## 8 Blended   12 weeks mvpa         0.950 0.170
## 9 Blended   24 weeks mvpa         0.956 0.240
dat_long |> group_by(time) |> levene_test(mvpa~treatment)
## # A tibble: 3 × 5
##   time       df1   df2 statistic     p
##   <fct>    <int> <int>     <dbl> <dbl>
## 1 Baseline     2    87     2.29  0.107
## 2 12 weeks     2    87     0.993 0.375
## 3 24 weeks     2    87     0.795 0.455
box_m(dat_wide[,c("mvpa_baseline","mvpa_12w","mvpa_24w")],dat_wide$treatment)
## # A tibble: 1 × 4
##   statistic p.value parameter method                                            
##       <dbl>   <dbl>     <dbl> <chr>                                             
## 1      8.87   0.714        12 Box's M-test for Homogeneity of Covariance Matric…
aov2 <- aov_ez(id="id",dv="mvpa",data=dat_long,
                between="treatment",within="time",
                anova_table=list(es=c("ges","pes"),correction="GG"))
aov2
## Anova Table (Type 3 tests)
## 
## Response: mvpa
##           Effect           df     MSE          F  ges  pes p.value
## 1      treatment        2, 87 3733.77  16.03 *** .238 .269   <.001
## 2           time 1.97, 171.72  336.52 246.11 *** .299 .739   <.001
## 3 treatment:time 3.95, 171.72  336.52  42.35 *** .128 .493   <.001
## ---
## Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '+' 0.1 ' ' 1
## 
## Sphericity correction method: GG
summary(aov2)     # Mauchly + GG/HF
## Warning in summary.Anova.mlm(object$Anova, multivariate = FALSE): HF eps > 1
## treated as 1
## 
## Univariate Type III Repeated-Measures ANOVA Assuming Sphericity
## 
##                  Sum Sq num Df Error SS den Df  F value    Pr(>F)    
## (Intercept)    10329789      1   324838     87 2766.586 < 2.2e-16 ***
## treatment        119738      2   324838     87   16.035  1.18e-06 ***
## time             163470      2    57788    174  246.106 < 2.2e-16 ***
## treatment:time    56257      4    57788    174   42.347 < 2.2e-16 ***
## ---
## Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
## 
## 
## Mauchly Tests for Sphericity
## 
##                Test statistic p-value
## time                  0.98672 0.56267
## treatment:time        0.98672 0.56267
## 
## 
## Greenhouse-Geisser and Huynh-Feldt Corrections
##  for Departure from Sphericity
## 
##                 GG eps Pr(>F[GG])    
## time           0.98689  < 2.2e-16 ***
## treatment:time 0.98689  < 2.2e-16 ***
## ---
## Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
## 
##                  HF eps   Pr(>F[HF])
## time           1.009645 1.877247e-51
## treatment:time 1.009645 9.054597e-25
eta_squared(aov2,partial=TRUE)
## # Effect Size for ANOVA (Type III)
## 
## Parameter      | Eta2 (partial) |       95% CI
## ----------------------------------------------
## treatment      |           0.27 | [0.14, 1.00]
## time           |           0.74 | [0.69, 1.00]
## treatment:time |           0.49 | [0.40, 1.00]
## 
## - One-sided CIs: upper bound fixed at [1.00].
# simple effects dan post hoc
joint_tests(aov2,by="treatment")
## treatment = Control:
##  model term df1 df2 F.ratio p.value
##  time         2  87  32.011 <0.0001
## 
## treatment = Web-based:
##  model term df1 df2 F.ratio p.value
##  time         2  87  29.185 <0.0001
## 
## treatment = Blended:
##  model term df1 df2 F.ratio p.value
##  time         2  87 300.114 <0.0001
joint_tests(aov2,by="time")
## time = Baseline:
##  model term df1 df2 F.ratio p.value
##  treatment    2  87   0.118  0.8888
## 
## time = X12.weeks:
##  model term df1 df2 F.ratio p.value
##  treatment    2  87  24.304 <0.0001
## 
## time = X24.weeks:
##  model term df1 df2 F.ratio p.value
##  treatment    2  87  35.392 <0.0001
em2 <- emmeans(aov2,~time|treatment)
contrast(em2,"trt.vs.ctrl",ref=1,adjust="holm")
## treatment = Control:
##  contrast             estimate   SE df t.ratio p.value
##  X12.weeks - Baseline     24.5 4.49 87   5.461 <0.0001
##  X24.weeks - Baseline     35.4 4.66 87   7.587 <0.0001
## 
## treatment = Web-based:
##  contrast             estimate   SE df t.ratio p.value
##  X12.weeks - Baseline     22.3 4.49 87   4.968 <0.0001
##  X24.weeks - Baseline     34.2 4.66 87   7.342 <0.0001
## 
## treatment = Blended:
##  contrast             estimate   SE df t.ratio p.value
##  X12.weeks - Baseline     81.6 4.49 87  18.180 <0.0001
##  X24.weeks - Baseline    104.8 4.66 87  22.486 <0.0001
## 
## P value adjustment: holm method for 2 tests
em2b <- emmeans(aov2,~treatment|time)
pairs(em2b,adjust="tukey")
## time = Baseline:
##  contrast              estimate   SE df t.ratio p.value
##  Control - (Web-based)   -4.281 9.84 87  -0.435  0.9010
##  Control - Blended       -3.980 9.84 87  -0.405  0.9138
##  (Web-based) - Blended    0.301 9.84 87   0.031  0.9995
## 
## time = X12.weeks:
##  contrast              estimate   SE df t.ratio p.value
##  Control - (Web-based)   -2.070 9.95 87  -0.208  0.9764
##  Control - Blended      -61.090 9.95 87  -6.139 <0.0001
##  (Web-based) - Blended  -59.021 9.95 87  -5.931 <0.0001
## 
## time = X24.weeks:
##  contrast              estimate   SE df t.ratio p.value
##  Control - (Web-based)   -3.141 9.87 87  -0.318  0.9458
##  Control - Blended      -73.441 9.87 87  -7.440 <0.0001
##  (Web-based) - Blended  -70.300 9.87 87  -7.122 <0.0001
## 
## P value adjustment: tukey method for comparing a family of 3 estimates
# perubahan baseline -> 24 minggu
change_dat <- dat_wide |>
  mutate(change24=mvpa_24w-mvpa_baseline)
anova_test(data=change_dat,dv=change24,between=treatment,effect.size="pes")
## ANOVA Table (type II tests)
## 
##      Effect DFn DFd     F        p p<.05   pes
## 1 treatment   2  87 75.23 1.07e-19     * 0.634
change_dat |> tukey_hsd(change24~treatment)
## # A tibble: 3 × 9
##   term      group1    group2    null.value estimate conf.low conf.high    p.adj
## * <chr>     <chr>     <chr>          <dbl>    <dbl>    <dbl>     <dbl>    <dbl>
## 1 treatment Control   Web-based          0    -1.14    -16.9      14.6 9.84e- 1
## 2 treatment Control   Blended            0    69.5      53.7      85.2 3.09e-10
## 3 treatment Web-based Blended            0    70.6      54.9      86.3 3.09e-10
## # ℹ 1 more variable: p.adj.signif <chr>
# 5. LINEAR MIXED MODEL
lmm <- lmer(mvpa ~ treatment*time + (1|id),data=dat_long,REML=TRUE)
anova(lmm,ddf="Kenward-Roger")
## Type III Analysis of Variance Table with Kenward-Roger's method
##                Sum Sq Mean Sq NumDF DenDF F value    Pr(>F)    
## treatment       10650    5325     2    87  16.035  1.18e-06 ***
## time           163470   81735     2   174 246.106 < 2.2e-16 ***
## treatment:time  56257   14064     4   174  42.347 < 2.2e-16 ***
## ---
## Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
summary(lmm)
## Linear mixed model fit by REML. t-tests use Satterthwaite's method [
## lmerModLmerTest]
## Formula: mvpa ~ treatment * time + (1 | id)
##    Data: dat_long
## 
## REML criterion at convergence: 2510.2
## 
## Scaled residuals: 
##      Min       1Q   Median       3Q      Max 
## -2.07924 -0.58062  0.02088  0.58084  1.99674 
## 
## Random effects:
##  Groups   Name        Variance Std.Dev.
##  id       (Intercept) 1133.9   33.67   
##  Residual              332.1   18.22   
## Number of obs: 270, groups:  id, 90
## 
## Fixed effects:
##                  Estimate Std. Error      df t value Pr(>|t|)    
## (Intercept)       195.598      3.719  87.000  52.598  < 2e-16 ***
## treatment1        -16.445      5.259  87.000  -3.127   0.0024 ** 
## treatment2        -13.281      5.259  87.000  -2.525   0.0134 *  
## time1             -33.654      1.568 174.000 -21.457  < 2e-16 ***
## time2               9.166      1.568 174.000   5.844 2.46e-08 ***
## treatment1:time1   13.691      2.218 174.000   6.172 4.60e-09 ***
## treatment2:time1   14.808      2.218 174.000   6.676 3.17e-10 ***
## treatment1:time2   -4.609      2.218 174.000  -2.078   0.0392 *  
## treatment2:time2   -5.703      2.218 174.000  -2.571   0.0110 *  
## ---
## Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
## 
## Correlation of Fixed Effects:
##             (Intr) trtmn1 trtmn2 time1  time2  trt1:1 trt2:1 trt1:2
## treatment1   0.000                                                 
## treatment2   0.000 -0.500                                          
## time1        0.000  0.000  0.000                                   
## time2        0.000  0.000  0.000 -0.500                            
## trtmnt1:tm1  0.000  0.000  0.000  0.000  0.000                     
## trtmnt2:tm1  0.000  0.000  0.000  0.000  0.000 -0.500              
## trtmnt1:tm2  0.000  0.000  0.000  0.000  0.000 -0.500  0.250       
## trtmnt2:tm2  0.000  0.000  0.000  0.000  0.000  0.250 -0.500 -0.500
performance::icc(lmm)
## # Intraclass Correlation Coefficient
## 
##     Adjusted ICC: 0.773
##   Unadjusted ICC: 0.416