Fat Liking Study

Author

May

Published

March 24, 2026

Questions

Plant-based milk is a growing marker, especially in young women. Although generally considered a healthier alternative compared to cow’s milk by consumers, some plant-based milk may contain high levels of fat and sugar, which may off-set some of the benefits of switching from cow’s milk to plant-based milk. The goal of this study is to test whether liking for fat and sugar may interact with plant-based milk consumption to affect diet quality and body composition.

H1. Does H2.

Load packages and call data

Reliability

Code
# Define your function
reliability <- function(data, xvar, yvar, title) {
  ggplot(data, aes_string(x = xvar, y = yvar, label = "ID")) +
    geom_point() +
    geom_label_repel() +
    geom_abline(intercept = 0, slope = 1, color = "red", linetype = "dashed") +
    stat_cor() +
    ylim(0, 100) +
    xlim(0, 100) +
    ggtitle(title) +
    theme_light() +
    theme(
      axis.text = element_text(size = 10),
      axis.title = element_text(size = 12),
      plot.title = element_text(size = 14, face = "bold")
    )
}

## liking 

liking.plots <- list(
  reliability(oatmilk.liking.wide, "liking_S0F0.1", "liking_S0F0.2", "S0F0"),
  reliability(oatmilk.liking.wide, "liking_S1F0.1", "liking_S1F0.2", "S1F0"),
  reliability(oatmilk.liking.wide, "liking_S1F1.1", "liking_S1F1.2", "S1F1"),
  reliability(oatmilk.liking.wide, "liking_S1F2.1", "liking_S1F2.2", "S1F2"),
  reliability(oatmilk.liking.wide, "liking_S1F3.1", "liking_S1F3.2", "S1F3"),
  reliability(oatmilk.liking.wide, "liking_S2F0.1", "liking_S2F0.2", "S2F0"),
  reliability(oatmilk.liking.wide, "liking_S2F1.1", "liking_S2F1.2", "S2F1"),
  reliability(oatmilk.liking.wide, "liking_S2F2.1", "liking_S2F2.2", "S2F2"),
  reliability(oatmilk.liking.wide, "liking_S2F3.1", "liking_S2F3.2", "S2F3")
)

# liking plot grid
(liking.plots[[1]] + liking.plots[[2]] + liking.plots[[3]]) /
(liking.plots[[4]] + liking.plots[[5]] + liking.plots[[6]]) /
(liking.plots[[7]] + liking.plots[[8]] + liking.plots[[9]])

Code
# sweet 
sweet.plots <- list(
  reliability(oatmilk.sweet.wide, "sweet_S0F0.1", "sweet_S0F0.2", "S0F0"),
  reliability(oatmilk.sweet.wide, "sweet_S1F0.1", "sweet_S1F0.2", "S1F0"),
  reliability(oatmilk.sweet.wide, "sweet_S1F1.1", "sweet_S1F1.2", "S1F1"),
  reliability(oatmilk.sweet.wide, "sweet_S1F2.1", "sweet_S1F2.2", "S1F2"),
  reliability(oatmilk.sweet.wide, "sweet_S1F3.1", "sweet_S1F3.2", "S1F3"),
  reliability(oatmilk.sweet.wide, "sweet_S2F0.1", "sweet_S2F0.2", "S2F0"),
  reliability(oatmilk.sweet.wide, "sweet_S2F1.1", "sweet_S2F1.2", "S2F1"),
  reliability(oatmilk.sweet.wide, "sweet_S2F2.1", "sweet_S2F2.2", "S2F2"),
  reliability(oatmilk.sweet.wide, "sweet_S2F3.1", "sweet_S2F3.2", "S2F3")
  )

# sweet plot grid
(sweet.plots[[1]] + sweet.plots[[2]] + sweet.plots[[3]]) /
(sweet.plots[[4]] + sweet.plots[[5]] + sweet.plots[[6]]) /
(sweet.plots[[7]] + sweet.plots[[8]] + sweet.plots[[9]])

Code
# creamy
creamy.plots <- list(
  reliability(oatmilk.creamy.wide, "creamy_S0F0.1", "creamy_S0F0.2", "S0F0"),
  reliability(oatmilk.creamy.wide, "creamy_S1F0.1", "creamy_S1F0.2", "S1F0"),
  reliability(oatmilk.creamy.wide, "creamy_S1F1.1", "creamy_S1F1.2", "S1F1"),
  reliability(oatmilk.creamy.wide, "creamy_S1F2.1", "creamy_S1F2.2", "S1F2"),
  reliability(oatmilk.creamy.wide, "creamy_S1F3.1", "creamy_S1F3.2", "S1F3"),
  reliability(oatmilk.creamy.wide, "creamy_S2F0.1", "creamy_S2F0.2", "S2F0"),
  reliability(oatmilk.creamy.wide, "creamy_S2F1.1", "creamy_S2F1.2", "S2F1"),
  reliability(oatmilk.creamy.wide, "creamy_S2F2.1", "creamy_S2F2.2", "S2F2"),
  reliability(oatmilk.creamy.wide, "creamy_S2F3.1", "creamy_S2F3.2", "S2F3")
)

# creamy plot grid
(creamy.plots[[1]] + creamy.plots[[2]] + creamy.plots[[3]]) /
(creamy.plots[[4]] + creamy.plots[[5]] + creamy.plots[[6]]) /
(creamy.plots[[7]] + creamy.plots[[8]] + creamy.plots[[9]])

Code
# bitter
bitter.plots <- list(
  reliability(oatmilk.bitter.wide, "bitter_S0F0.1", "bitter_S0F0.2", "S0F0"),
  reliability(oatmilk.bitter.wide, "bitter_S1F0.1", "bitter_S1F0.2", "S1F0"),
  reliability(oatmilk.bitter.wide, "bitter_S1F1.1", "bitter_S1F1.2", "S1F1"),
  reliability(oatmilk.bitter.wide, "bitter_S1F2.1", "bitter_S1F2.2", "S1F2"),
  reliability(oatmilk.bitter.wide, "bitter_S1F3.1", "bitter_S1F3.2", "S1F3"),
  reliability(oatmilk.bitter.wide, "bitter_S2F0.1", "bitter_S2F0.2", "S2F0"),
  reliability(oatmilk.bitter.wide, "bitter_S2F1.1", "bitter_S2F1.2", "S2F1"),
  reliability(oatmilk.bitter.wide, "bitter_S2F2.1", "bitter_S2F2.2", "S2F2"),
  reliability(oatmilk.bitter.wide, "bitter_S2F3.1", "bitter_S2F3.2", "S2F3")
)

# bitter plot grid
(bitter.plots[[1]] + bitter.plots[[2]] + bitter.plots[[3]]) /
(bitter.plots[[4]] + bitter.plots[[5]] + bitter.plots[[6]]) /
(bitter.plots[[7]] + bitter.plots[[8]] + bitter.plots[[9]])

Decoding surveys

Code
## Liking score
liking.df <- qualtrics %>% 
  select("ID", "FL-01_3":"FL-60_3") %>%
  mutate(veg.liking = rowMeans(select(., "FL-01_3":"FL-06_3"), na.rm = TRUE), 
         veg.liking = (veg.liking+100)/2, 
         fruit.liking = rowMeans(select(., "FL-07_3":"FL-11_3"), na.rm = TRUE), 
         fruit.liking = (fruit.liking+100)/2, 
         saltyfat.liking = rowMeans(select(., "FL-12_3":"FL-15_3"), na.rm = TRUE), 
         saltyfat.liking = (saltyfat.liking+100)/2,
         hfprotein.liking = rowMeans(select(., "FL-16_3":"FL-20_3"), na.rm = TRUE),   
         hfprotein.liking = (hfprotein.liking+100)/2, 
         alcohol.liking = rowMeans(select(., "FL-22_3":"FL-25_3"), na.rm = TRUE), 
         alcohol.liking = (alcohol.liking+100)/2,
         wg.liking = rowMeans(select(., "FL-26_3":"FL-29_3"), na.rm = TRUE), 
         wg.liking = (wg.liking+100)/2,
         carbs.liking = rowMeans(select(., "FL-30_3":"FL-34_3"), na.rm = TRUE), 
         carbs.liking = (carbs.liking+100)/2,
         healthyfat.liking = rowMeans(select(., "FL-35_3":"FL-38_3"), na.rm = TRUE), 
         healthyfat.liking = (healthyfat.liking+100)/2,
        sweets.liking = rowMeans(select(., "FL-39_3":"FL-43_3"), na.rm = TRUE),
        sweets.liking = (sweets.liking+100)/2,
        ssb.liking = rowMeans(select(., "FL-44_3":"FL-47_3"), na.rm = TRUE),
        ssb.liking = (ssb.liking+100)/2,
        sfbl.liking = rowMeans(select(., "FL-39_3":"FL-47_3"), na.rm = TRUE),
        sfbl.liking = (sfbl.liking+100)/2,
        sufat.liking = rowMeans(select(., c("FL-39_3","FL-40_3", "FL-43_3")), na.rm = TRUE),
        sufat.liking = (sufat.liking+100)/2,
         unhealthyfat.liking = rowMeans(select(., "FL-48_3":"FL-52_3"), na.rm = TRUE),
        unhealthyfat.liking = (unhealthyfat.liking+100)/2,
         protein.liking = rowMeans(select(., "FL-53_3":"FL-57_3"), na.rm = TRUE), 
        protein.liking = (protein.liking+100)/2,
         spicy.liking = rowMeans(select(., "FL-58_3":"FL-60_3"), na.rm = TRUE),
        spicy.liking = (spicy.liking+100)/2,) %>%
  select(c("ID", ends_with(".liking")))

## Three factor questionnaire
TFQ.df <- qualtrics %>% 
  select("ID", "TFQ-01":"TFQ-21") %>%
  mutate(uncontrolled = rowSums(select(., "TFQ-03", "TFQ-06", "TFQ-08", "TFQ-09", "TFQ-12", "TFQ-13", "TFQ-15", "TFQ-19", "TFQ-20"), na.rm = TRUE)) %>%  
  mutate(uncontrolled = ((uncontrolled-1)/36)*100, na.rm = TRUE) %>%
  mutate(restraint = rowSums(select(., "TFQ-01", "TFQ-05", "TFQ-11"), na.rm = TRUE)) %>%
  mutate(restraint = ((restraint-1)/12)*100, na.rm = TRUE) %>%
  mutate(emotional = rowSums(select(., "TFQ-02", "TFQ-04", "TFQ-07", "TFQ-10", "TFQ-14", "TFQ-16"), na.rm = TRUE)) %>%
  mutate(emotional = ((emotional-1)/24)*100, na.rm = TRUE) %>%
    select(c("ID", "uncontrolled", "restraint", "emotional")) 

## Body appreciation scale 
BAS.df <- qualtrics %>% 
  select("ID", starts_with("BAS")) %>%
  mutate(BAS = rowSums(select(., 2:11), na.rm = TRUE))%>%
  select(c("ID", "BAS")) 

## Intuitive eating scale 
IES.df <- qualtrics %>% 
  select("ID", starts_with("IES")) %>%
  mutate(IES = (rowSums(select(., 2:24), na.rm = TRUE))/23) %>%
  select(c("ID", "IES"))

## sHEI score
HEI.df <- qualtrics %>%
  select("ID", "sex", "Fruit":"Water") %>%
  mutate(fruit.1 = case_when(
    Fruit == 1 ~ 0,
    Fruit == 2 ~ 2, 
    Fruit == 3 ~ 3.5,
    Fruit >= 4 ~ 5)) %>%
  mutate(fruit.2 = case_when (
    Juice == 1 ~ 0,
    Juice == 2 ~ 2,
    Juice == 3 ~ 3.5,
    Juice >= 4 ~ 5)) %>% 
  mutate(tfruitHEI = case_when(
    fruit.1 + fruit.2 <5 ~ 0,
    fruit.1 + fruit.2 >= 5 ~ 5)) %>%
  mutate(wfruitHEI = case_when(
    Fruit == 1 ~ 0,
    Fruit == 2 ~ 2.5, 
    Fruit >= 3 ~ 5)) %>%
  mutate(vegHEI = case_when(
    `Green veg` == 1 ~ 1.6,
    `Green veg` == 2 & `Starchy veg` >= 2 ~ 2.46,
    `Green veg` >= 2 & `Starchy veg` >= 2 ~ 3.24,
    `Green veg` >= 2 & `Starchy veg` == 1 ~ 3.56)) %>%
  mutate(bean.1 = case_when(
    `Green veg` == 1 ~ 0,
    `Green veg` >= 2 ~5)) %>%
  mutate(bean.2 = case_when(
    Beans == 1 ~ 0,
    Beans >= 2 ~ 5)) %>%
  mutate(beanHEI = case_when(
    bean.1 + bean.2 < 5 ~ 0,
    bean.1 + bean.2 >= 5 ~ 5)) %>%
  mutate(wgHEI = case_when(
    `Whole grains.day` == 1 ~ 0.51,
    sex == 1 & `Whole grains.day` >= 2 ~ 2.97,
    sex == 2 & `Whole grains.day` >= 2 & `Whole grains.day` <= 3 ~ 5.20,
    sex == 2 & `Whole grains.day` >= 4 ~ 6.94)) %>%
  mutate(dairyHEI = case_when(
    sex == 1 & `Milk.day` <= 3 ~ 3.22,
    sex == 2 & `Milk.day` <= 3 & `Low-fat milk.day` == 1 ~ 3.32,
    sex == 2 & `Milk.day` <= 3 & `Low-fat milk.day` >= 2 ~ 4.81,
    `Milk.day` >= 4 ~ 6.51)) %>%
  mutate(tproteinHEI = case_when(
    sex == 1 & `Seafood.freq` <= 4 ~ 4.11,
    sex == 1 & `Seafood.freq` >= 5 ~ 4.98,
    sex == 1 & is.na(`Seafood.freq`) ~ 4.11,
    sex == 2 ~ 4.97)) %>%
  mutate(sfpproteinHEI = case_when(
    sex == 1 & Nuts <= 2 ~ 0.49,
    sex == 2 & Nuts <= 2 ~ 1.50,
    Nuts >= 3 ~ 4.20)) %>%
  mutate(fatHEI = case_when(
    `Milk.day` >= 4 ~ 2.56,
    `Saturated fats` >= 2 & `Saturated fats` <= 3 & `Milk.freq` >= 1 & `Low-fat milk.freq` <= 2 ~ 2.63,
    `Saturated fats` >= 2 & `Saturated fats` <= 3 & is.na(`Milk.freq`) | is.na(`Low-fat milk.freq`) ~ 2.63,
    `Saturated fats` >= 2 & `Saturated fats` <= 3 & `Milk.freq` >= 1 & `Low-fat milk.freq` >= 3 ~ 4.54,
    `Saturated fats` == 1 & `Milk.freq` >= 1 ~ 5.93,
    `Saturated fats` == 1 & is.na(`Milk.freq`) ~ 5.93)) %>%
  mutate(grainHEI = case_when(
    `Green veg` == 1 ~ 2.13,
    `Grains.day` >= 3 & `Seafood.day` >= 2 & `Green veg` >= 2 ~ 2.27,
    `Grains.day` >= 3 & Nuts >= 1 & Nuts <= 2 & `Seafood.day` == 1 & `Green veg` >= 2 ~ 4.73,
    `Grains.day` >= 3 & Nuts >= 3 & `Seafood.day` == 1 & `Green veg` >= 2 ~ 8.45,
    `Grains.day` >= 1 & `Grains.day` <= 2 & `Green veg` >= 2 ~ 9.25)) %>%
  mutate(sodiumHEI = case_when(
    Fruit >= 1 & Fruit <= 2 & `Grains.day` >= 3 & Water == 3 ~ 0.70,
    Fruit >= 3 & `Grains.day` >= 3 & Water == 3 ~ 2.30,
    `Grains.day` >= 3 & Water >= 1 & Water <= 2 ~ 4.94,
    `Grains.day` >= 1 & `Grains.day` <= 2 ~ 6.07)) %>%
  mutate(ssb.cal = case_when(
    `SSB.day` == 1  ~ 0,
    `SSB.day` == 2 ~ 156,
    `SSB.day` == 3 ~ 312,
    `SSB.day` == 4 ~ 468,
    `SSB.day` == 5 ~ 624,
    `SSB.day` == 6 ~ 780,
    `SSB.day` == 7 ~ 936),
    sugar.cal = case_when(
    `Added sugars` == 1 ~ 130,
    `Added sugars` == 2 ~ 260,
    `Added sugars` == 3 ~ 520)) %>%
  mutate(sugar.intake = (ssb.cal + sugar.cal)) %>%
  mutate(sugarHEI = case_when(
    sugar.intake <= 130 ~ 10,
    sugar.intake > 130 & sugar.cal < 520 ~ 5,
    sugar.intake >= 520 ~ 0)) %>%
  mutate(sugar.tsp = case_when(
    `SSB.freq` <= 4 ~ 13.26,
    `SSB.freq` >= 5 & `SSB.freq` <=6 ~ 16.00,
    `SSB.day` ==2 ~ 16.00,
    `SSB.day` >=3 ~ 26.87)) %>%
  mutate(satfatHEI = case_when(
    `SSB.day` >= 3 ~ 1.82,
    `SSB.day` <= 2 & `Grains.day` <= 2 ~ 3.20,
    `SSB.day` <= 2 & `Grains.day` >= 3 & Nuts <= 2 ~ 4.64,
    `SSB.day` <= 2 & `Grains.day` >= 3 & Nuts >= 3 ~ 6.56)) %>%
  select("ID", "sugar.intake", "sugar.tsp", ends_with("HEI")) %>%
  mutate(sHEI = rowSums(select(., "tfruitHEI":"satfatHEI"), na.rm = TRUE)) %>%
  mutate(SuFatHEI = rowSums(select(., c("sugarHEI", "satfatHEI")))) 

## Putting scores together
qualtrics$ID <- as.character(qualtrics$ID)
anthro$ID <- as.character(anthro$ID)
oatmilk.liking.wide$ID <- as.character(oatmilk.liking.wide$ID) 
oatmilk.sweet.wide$ID <- as.character(oatmilk.sweet.wide$ID) 
oatmilk.creamy.wide$ID <- as.character(oatmilk.creamy.wide$ID) 
oatmilk.bitter.wide$ID <- as.character(oatmilk.bitter.wide$ID) 
liking.df$ID <- as.character(liking.df$ID)
HEI.df$ID <- as.character(HEI.df$ID)
TFQ.df$ID <- as.character(TFQ.df$ID)
BAS.df$ID <- as.character(BAS.df$ID)
IES.df$ID <- as.character(IES.df$ID)

### Missing stress survey data

full.df <- qualtrics  %>%
  select(c("ID", "age", "race", "ethn", "usb", "education", "hinc", "exec", "plantmilk", "plantmilk_freq")) %>%
  left_join(anthro, by = "ID") %>%
  left_join(oatmilk.liking.wide, by = "ID") %>%
  left_join(oatmilk.sweet.wide, by = "ID") %>%
  left_join(oatmilk.creamy.wide, by = "ID") %>%
  left_join(oatmilk.bitter.wide, by = "ID") %>%
  left_join(liking.df, by = "ID") %>%
  left_join(HEI.df, by = "ID") %>%
  left_join(TFQ.df, by = "ID") %>%
  left_join(BAS.df, by = "ID") %>%
  left_join(IES.df, by = "ID") %>%
  left_join(bia, by  = "ID") %>%
  mutate(BMIcat = case_when(
      BMI < 18.5 ~ "0",
      BMI >= 18.5 & BMI  < 25 & race != "Asian" ~ "1",
      BMI >= 25 & BMI < 30 & race != "Asian" ~ "2",
      BMI > 30 & race != "Asian" ~ "3",
      BMI >= 18.5 & BMI  < 23 & race == "Asian" ~ "1",
      BMI >= 23 & BMI < 25 & race == "Asian" ~ "2",
      BMI > 25 & race == "Asian" ~ "3"))  %>%
  mutate(sugarcat = ntile(sugar.intake, 3)) %>%
  mutate(DQ = ntile(sHEI, 3)) %>%
  mutate(sweetPref = case_when(
      sweetpref.atF2 == 1 ~ "Low",
      sweetpref.atF2 == 2 ~ "High")) %>%
  mutate(fatPref = case_when(
    fatpref.atS1 == 1 ~ "Low",
    fatpref.atS1 == 2 ~ "Medium",
    fatpref.atS1 == 3 ~ "High"))

## Joining sweetPref with oat milk dfs
sweetPref <- full.df %>% select(ID, sweetPref)

oatmilk.liking.long <- oatmilk.liking.long %>%  
  left_join(sweetPref, by = "ID") 
oatmilk.sweet.long <- oatmilk.sweet.long %>%  
  left_join(sweetPref, by = "ID") 
oatmilk.creamy.long <- oatmilk.creamy.long %>%  
  left_join(sweetPref, by = "ID") 
oatmilk.bitter.long <- oatmilk.bitter.long %>%  
  left_join(sweetPref, by = "ID") 

oatmilk.liking.wide <- oatmilk.liking.wide %>%  
  left_join(sweetPref, by = "ID") 
oatmilk.sweet.wide <- oatmilk.sweet.wide %>%  
  left_join(sweetPref, by = "ID") 
oatmilk.creamy.wide <- oatmilk.creamy.wide %>%  
  left_join(sweetPref, by = "ID") 
oatmilk.bitter.wide <- oatmilk.bitter.wide %>%  
  left_join(sweetPref, by = "ID") 

## Joining fatPref with oat milk dfs
fatPref <- full.df %>% select(ID, fatPref)

oatmilk.liking.long <- oatmilk.liking.long %>%  
  left_join(fatPref, by = "ID") 
oatmilk.sweet.long <- oatmilk.sweet.long %>%  
  left_join(fatPref, by = "ID") 
oatmilk.creamy.long <- oatmilk.creamy.long %>%  
  left_join(fatPref, by = "ID") 
oatmilk.bitter.long <- oatmilk.bitter.long %>%  
  left_join(fatPref, by = "ID") 

oatmilk.liking.wide <- oatmilk.liking.wide %>%  
  left_join(fatPref, by = "ID") 
oatmilk.sweet.wide <- oatmilk.sweet.wide %>%  
  left_join(fatPref, by = "ID") 
oatmilk.creamy.wide <- oatmilk.creamy.wide %>%  
  left_join(fatPref, by = "ID") 
oatmilk.bitter.wide <- oatmilk.bitter.wide %>%  
  left_join(fatPref, by = "ID") 

full.df$sweetPref <- factor(full.df$sweetPref , levels = c("Low", "High"))
full.df$fatPref <- factor(full.df$fatPref , levels = c("Low", "Medium", "High"))
full.df$prefcal.cat <- factor(full.df$prefcal.cat , levels = c("1", "2", "3"))

Preference data frames

Code
pref.df <- oatmilk.liking.wide %>%
  select(ID, 
         # Rep 1
         liking_S1F0.1, liking_S2F0.1, liking_S1F1.1, liking_S1F2.1, liking_S1F3.1,
         liking_S1F2.1, liking_S2F2.1,
         # Rep 2
         liking_S1F0.2, liking_S2F0.2, liking_S1F1.2, liking_S1F2.2, liking_S1F3.2,
         liking_S1F2.2, liking_S2F2.2,
         # Overall (averaged across reps)
         liking_S1F0, liking_S2F0, liking_S1F1, liking_S1F2, liking_S1F3,
         liking_S2F2,
         # Other variables
         pref.cal, prefcal.cat) %>%
  rowwise() %>%
  mutate(
    # Fat preference rep 1 (at S1)
    fatPref.1 = case_when(
      `liking_S1F1.1` == max(c(`liking_S1F1.1`, `liking_S1F2.1`, `liking_S1F3.1`), na.rm = TRUE) ~ "low",
      `liking_S1F2.1` == max(c(`liking_S1F1.1`, `liking_S1F2.1`, `liking_S1F3.1`), na.rm = TRUE) ~ "medium",
      `liking_S1F3.1` == max(c(`liking_S1F1.1`, `liking_S1F2.1`, `liking_S1F3.1`), na.rm = TRUE) ~ "high"
    ),
    
    # Fat preference rep 2 (at S1)
    fatPref.2 = case_when(
      `liking_S1F1.2` == max(c(`liking_S1F1.2`, `liking_S1F2.2`, `liking_S1F3.2`), na.rm = TRUE) ~ "low",
      `liking_S1F2.2` == max(c(`liking_S1F1.2`, `liking_S1F2.2`, `liking_S1F3.2`), na.rm = TRUE) ~ "medium",
      `liking_S1F3.2` == max(c(`liking_S1F1.2`, `liking_S1F2.2`, `liking_S1F3.2`), na.rm = TRUE) ~ "high"
    ),
    
    # Fat preference overall (at S1) - using averaged liking scores
    fatPref = case_when(
      `liking_S1F1` == max(c(`liking_S1F1`, `liking_S1F2`, `liking_S1F3`), na.rm = TRUE) ~ "low",
      `liking_S1F2` == max(c(`liking_S1F1`, `liking_S1F2`, `liking_S1F3`), na.rm = TRUE) ~ "medium",
      `liking_S1F3` == max(c(`liking_S1F1`, `liking_S1F2`, `liking_S1F3`), na.rm = TRUE) ~ "high"
    ),
    
    # Sweet preference rep 1 (at F2)
    sweetPref.1 = case_when(
      `liking_S1F2.1` == max(c(`liking_S1F2.1`, `liking_S2F2.1`), na.rm = TRUE) ~ "low",
      `liking_S2F2.1` == max(c(`liking_S1F2.1`, `liking_S2F2.1`), na.rm = TRUE) ~ "high"
    ),
    
    # Sweet preference rep 2 (at F2)
    sweetPref.2 = case_when(
      `liking_S1F2.2` == max(c(`liking_S1F2.2`, `liking_S2F2.2`), na.rm = TRUE) ~ "low",
      `liking_S2F2.2` == max(c(`liking_S1F2.2`, `liking_S2F2.2`), na.rm = TRUE) ~ "high"
    ),
    
    # Sweet preference overall (at F2) - using averaged liking scores
    sweetPref = case_when(
      `liking_S1F2` == max(c(`liking_S1F2`, `liking_S2F2`), na.rm = TRUE) ~ "low",
      `liking_S2F2` == max(c(`liking_S1F2`, `liking_S2F2`), na.rm = TRUE) ~ "high"
    )
  ) %>%
  ungroup()

pref.df <- pref.df %>%
  mutate(
    # Relevel fat preferences (low, medium, high)
    fatPref = factor(fatPref, levels = c("low", "medium", "high")),
    fatPref.1 = factor(fatPref.1, levels = c("low", "medium", "high")),
    fatPref.2 = factor(fatPref.2, levels = c("low", "medium", "high")),
    
    # Relevel sweet preferences (low, high)
    sweetPref = factor(sweetPref, levels = c("low", "high")),
    sweetPref.1 = factor(sweetPref.1, levels = c("low", "high")),
    sweetPref.2 = factor(sweetPref.2, levels = c("low", "high"))
  )

Liking clusters

Code
# Step 1: Prepare PCA input data
pca.df <- full.df %>%
  select(ID, liking_S0F0, liking_S1F0, liking_S2F0, liking_S1F1, liking_S1F2, liking_S1F3, liking_S2F1, liking_S2F2, liking_S2F3) %>%
  drop_na()

# Step 2: Run PCA
res.pca <- pca.df %>%
  select(-ID) %>%
  prcomp(., scale. = TRUE)

# Step 3: Get PCA coordinates
pca_coords <- res.pca$x

# Step 4: K-means clustering
km.res <- kmeans(pca_coords, centers = 3, nstart = 25)

    # Elbow and silhouette for K-means
    fviz_nbclust(pca_coords, kmeans, method = "wss")

Code
    fviz_nbclust(pca_coords, kmeans, method = "silhouette")

Code
# Step 5: Hierarchical clustering

dist_matrix <- dist(pca_coords)
hc.res <- hclust(dist_matrix, method = "ward.D2")
hc.groups <- cutree(hc.res, k = 3)

    # Plot dendrogram
    plot(hc.res, labels = FALSE, hang = -1, main = "Dendrogram")

Code
# Step 6: Plot PCA biplot with K-means clusters
fviz_pca_biplot(res.pca,
                habillage = as.factor(km.res$cluster),
                addEllipses = TRUE,
                ellipse.level = 0.95,
                palette = "jco",
                repel = TRUE,
                label = "var") +
  ggtitle("PCA Biplot with K-means Clusters")
Warning: Using `size` aesthetic for lines was deprecated in ggplot2 3.4.0.
ℹ Please use `linewidth` instead.
ℹ The deprecated feature was likely used in the ggpubr package.
  Please report the issue at <https://github.com/kassambara/ggpubr/issues>.

Code
# Step 7: Plot PCA biplot with Hierarchical clusters
fviz_pca_biplot(res.pca,
                habillage = as.factor(hc.groups),
                addEllipses = TRUE,
                ellipse.level = 0.95,
                palette = "npg",
                repel = TRUE,
                label = "var") +
  ggtitle("PCA Biplot with Hierarchical Clusters")

Code
## See who is in the cluster (hierarchical)
pca_coords$ID <- as.character(pca.df$ID)
Warning in pca_coords$ID <- as.character(pca.df$ID): Coercing LHS to a list
Code
pca_coords$cluster <- as.factor(hc.groups)
pca_coords <- as.data.frame(pca_coords)

pca_coords %>%  
  group_by(cluster) %>%
  summarize(participants = paste(ID, collapse = " "))
# A tibble: 3 × 2
  cluster participants                                                          
  <fct>   <chr>                                                                 
1 1       3 8 7 11 18 19 21 31 36 38 39 50 54 61 62 68 76 81 101 114 122 130 13…
2 2       4 5 10 12 13 14 15 23 24 25 26 27 28 30 32 33 35 37 40 41 45 47 48 51…
3 3       6 9 16 17 20 22 29 34 42 43 44 46 49 56 57 69 70 80 88 90 96 99 102 1…
Code
cluster <- pca_coords %>% select(ID, cluster)

cluster %>%
  group_by(cluster) %>%
  count()
# A tibble: 3 × 2
# Groups:   cluster [3]
  cluster     n
  <fct>   <int>
1 1          30
2 2         113
3 3          37
Code
## Joining cluster with oat milk liking df 
full.df <- full.df  %>%
    left_join(cluster, by = "ID") 

oatmilk.liking.long$ID <- as.factor(oatmilk.liking.long$ID)

oatmilk.liking.long <- oatmilk.liking.long %>%  
  left_join(cluster, by = "ID") 

oatmilk.liking.wide <- oatmilk.liking.wide %>%  
  left_join(cluster, by = "ID") 

Fat liking slopes

Code
## Calculate the slopes for the low sweet samples 
slopes.s1.df <- oatmilk.liking.long %>%
  filter(sample %in% c("S0F0", "S1F1", "S1F2", "S1F3")) %>%
  mutate(fat.level = case_when(
    str_detect(sample, "S0F0") ~ 0, 
    str_detect(sample, "S1F1") ~ 0.33,
    str_detect(sample, "S1F2") ~ 0.67,
    str_detect(sample, "S1F3") ~ 1.0
  )) 

slopes.s1.df <- slopes.s1.df %>%
  filter(fat.level == c(0, 0.33, 0.67, 1.0)) %>%
  filter(!is.na(liking)) %>%
  group_by(ID) %>%
  nest() %>%
  mutate(model = map(data, ~lm(liking ~ fat.level, data = .x)),
         slope = map_dbl(model, ~coef(.)[2])) %>%
  rename(fatliking.s1 = slope) %>%
  select(c(ID, fatliking.s1)) 

slopes.s1.df <- slopes.s1.df  %>%
  mutate(fatPhen.s1 = case_when(
    fatliking.s1 <= -15 ~ 1,
    fatliking.s1 > -15 & fatliking.s1 < 15 ~ 2,
    fatliking.s1 >= 15 ~ 3 )) 

## Calculate the slopes for the high sweet samples 
slopes.s2.df <- oatmilk.liking.long %>%
  filter(sample %in% c("S0F0", "S2F1", "S2F2", "S2F3")) %>%
  mutate(fat.level = case_when(
    str_detect(sample, "S0F0") ~ 0, 
    str_detect(sample, "S2F1") ~ 0.33,
    str_detect(sample, "S2F2") ~ 0.67,
    str_detect(sample, "S2F3") ~ 1.0
  )) 

slopes.s2.df <- slopes.s2.df %>%
  filter(fat.level == c(0, 0.33, 0.67, 1.0)) %>%
  filter(!is.na(liking)) %>%
  group_by(ID) %>%
  nest() %>%
  mutate(model = map(data, ~lm(liking ~ fat.level, data = .x)),
         slope = map_dbl(model, ~coef(.)[2])) %>%
  rename(fatliking.s2 = slope) %>%
  select(c(ID, fatliking.s2)) 

slopes.s2.df <- slopes.s2.df  %>%
  mutate(fatPhen.s2 = case_when(
    fatliking.s2 <= -15 ~ 1,
    fatliking.s2 > -15 & fatliking.s2 < 15 ~ 2,
    fatliking.s2 >= 15 ~ 3 )) 

### Joining the dfs to create a slopes dataframe
fatlikingslopes.df <- slopes.s1.df  %>%
  select(c("ID", "fatliking.s1", "fatPhen.s1")) %>%
  left_join(slopes.s2.df, by = "ID") 

fatlikingslopes.df$ID <- as.factor(fatlikingslopes.df$ID)


## Joining fating liking slopes df with oat milk liking df 
full.df <- full.df  %>%
    left_join(fatlikingslopes.df, by = "ID") 

oatmilk.liking.long$ID <- as.factor(oatmilk.liking.long$ID)

oatmilk.liking.long <- oatmilk.liking.long %>%  
  left_join(fatlikingslopes.df, by = "ID")


oatmilk.liking.wide <- oatmilk.liking.wide %>%  
  left_join(fatlikingslopes.df, by = "ID")

Sweet liking slopes

Code
## Calculate the slopes for the fat-free samples 
slopes.f0.df <- oatmilk.liking.long %>%
  filter(sample %in% c("S0F0", "S1F0", "S2F0")) %>%
  mutate(sugar.level = case_when(
    str_detect(sample, "S0F0") ~ 0,
    str_detect(sample, "S1F0") ~ 0.5,
    str_detect(sample, "S2F0") ~ 1.0,
  )) 

slopes.f0.df <- slopes.f0.df %>%
  filter(sugar.level == c(0, 0.5, 1.0)) %>%
  filter(!is.na(liking)) %>%
  group_by(ID) %>%
  nest() %>%
  mutate(model = map(data, ~lm(liking ~ sugar.level, data = .x)),
         slope = map_dbl(model, ~coef(.)[2])) %>%
  rename(sweetliking.f0 = slope) %>%
  select(c(ID, sweetliking.f0)) 

slopes.f0.df <- slopes.f0.df  %>%
  mutate(sweetPhen.f0 = case_when(
    sweetliking.f0 <= -15 ~ 1,
    sweetliking.f0 > -15 & sweetliking.f0 < 15 ~ 2,
    sweetliking.f0 >= 15 ~ 3 )) 

## Calculate the slopes for the low fat samples 
slopes.f1.df <- oatmilk.liking.long %>%
  filter(sample %in% c("S0F0", "S1F1", "S2F1")) %>%
  mutate(sugar.level = case_when(
    str_detect(sample, "S0F0") ~ 0,
    str_detect(sample, "S1F1") ~ 0.5,
    str_detect(sample, "S2F1") ~ 1.0,
  )) 

slopes.f1.df <- slopes.f1.df %>%
  filter(sugar.level == c(0, 0.5, 1.0)) %>%
  filter(!is.na(liking)) %>%
  group_by(ID) %>%
  nest() %>%
  mutate(model = map(data, ~lm(liking ~ sugar.level, data = .x)),
         slope = map_dbl(model, ~coef(.)[2])) %>%
  rename(sweetliking.f1 = slope) %>%
  select(c(ID, sweetliking.f1)) 

slopes.f1.df <- slopes.f1.df  %>%
  mutate(sweetPhen.f1 = case_when(
    sweetliking.f1 <= -15 ~ 1,
    sweetliking.f1 > -15 & sweetliking.f1 < 15 ~ 2,
    sweetliking.f1 >= 15 ~ 3 )) 

## Calculate the slopes for the middle fat samples 
slopes.f2.df <- oatmilk.liking.long %>%
  filter(sample %in% c("S0F0", "S1F2", "S2F2")) %>%
  mutate(sugar.level = case_when(
    str_detect(sample, "S0F0") ~ 0, 
    str_detect(sample, "S1F2") ~ 0.5,
    str_detect(sample, "S2F2") ~ 1.,
  )) 

slopes.f2.df <- slopes.f2.df %>%
  filter(sugar.level == c(0, 0.5, 1.0)) %>%
  filter(!is.na(liking)) %>%
  group_by(ID) %>%
  nest() %>%
  mutate(model = map(data, ~lm(liking ~ sugar.level, data = .x)),
         slope = map_dbl(model, ~coef(.)[2])) %>%
  rename(sweetliking.f2 = slope) %>%
  select(c(ID, sweetliking.f2)) 

slopes.f2.df <- slopes.f2.df  %>%
  mutate(sweetPhen.f2 = case_when(
    sweetliking.f2 <= -15 ~ 1,
    sweetliking.f2 > -15 & sweetliking.f2 < 15 ~ 2,
    sweetliking.f2 >= 15 ~ 3 )) 

## Calculate the slopes for the high fat samples 
slopes.f3.df <- oatmilk.liking.long %>%
  filter(sample %in% c("S0F0", "S1F3", "S2F3")) %>%
  mutate(sugar.level = case_when(
    str_detect(sample, "S0F0") ~ 0,
    str_detect(sample, "S1F3") ~ 0.5,
    str_detect(sample, "S2F3") ~ 1.0,
  )) 

slopes.f3.df <- slopes.f3.df %>%
  filter(sugar.level == c(0, 0.5, 1.0)) %>%
  filter(!is.na(liking)) %>%
  group_by(ID) %>%
  nest() %>%
  mutate(model = map(data, ~lm(liking ~ sugar.level, data = .x)),
         slope = map_dbl(model, ~coef(.)[2])) %>%
  rename(sweetliking.f3 = slope) %>%
  select(c(ID, sweetliking.f3)) 

slopes.f3.df <- slopes.f3.df  %>%
  mutate(sweetPhen.f3 = case_when(
    sweetliking.f3 <= -15 ~ 1,
    sweetliking.f3 > -15 & sweetliking.f3 < 15 ~ 2,
    sweetliking.f3 >= 15 ~ 3 )) 


### Joining the dfs to create a slopes dataframe
sweetlikingslopes.df <- slopes.f0.df  %>%
  select(c("ID", "sweetliking.f0", "sweetPhen.f0")) %>%
    left_join(slopes.f1.df, by = "ID") %>%
    left_join(slopes.f2.df, by = "ID") %>%
    left_join(slopes.f3.df, by = "ID")

sweetlikingslopes.df$ID <- as.factor(sweetlikingslopes.df$ID)

## Joining sweet liking slopes with oat milk liking df 
full.df <- full.df  %>%
    left_join(sweetlikingslopes.df, by = "ID") 

oatmilk.liking.long$ID <- as.factor(oatmilk.liking.long$ID)

oatmilk.liking.long <- oatmilk.liking.long %>%  
  left_join(sweetlikingslopes.df, by ="ID") 

oatmilk.liking.wide <- oatmilk.liking.wide %>%  
  left_join(sweetlikingslopes.df, by ="ID") 

Counts

Code
oatmilk.liking.wide %>%
  group_by(pref.cal) %>%
  count()
# A tibble: 9 × 2
# Groups:   pref.cal [9]
  pref.cal     n
     <dbl> <int>
1       0     22
2      90     11
3     118     29
4     120      9
5     134.    15
6     148     39
7     160     15
8     188     30
9     269.    10
Code
oatmilk.liking.wide %>%
  group_by(fatpref.atS1) %>%
  count()
# A tibble: 3 × 2
# Groups:   fatpref.atS1 [3]
  fatpref.atS1     n
  <chr>        <int>
1 1               46
2 2               70
3 3               64
Code
full.df %>%
  count(sweetpref.atF2)
# A tibble: 2 × 2
  sweetpref.atF2     n
  <chr>          <int>
1 1                 40
2 2                140
Code
full.df %>%
  count(fatpref.atS1)
# A tibble: 3 × 2
  fatpref.atS1     n
  <chr>        <int>
1 1               46
2 2               70
3 3               64
Code
full.df %>%
  count(cluster)
# A tibble: 3 × 2
  cluster     n
  <fct>   <int>
1 1          30
2 2         113
3 3          37

Participants flow - Sankey diagram

Code
## Fat preference flow: fatPref → fatPref.1 → fatPref.2
fat_flow <- pref.df %>%
  select(ID, fatPref, fatPref.1, fatPref.2) %>%
  count(fatPref, fatPref.1, fatPref.2) %>%
  filter(!is.na(fatPref) & !is.na(fatPref.1) & !is.na(fatPref.2))

ggplot(fat_flow, 
       aes(axis1 = fatPref, axis2 = fatPref.1, axis3 = fatPref.2, y = n)) +
  geom_alluvium(aes(fill = fatPref), width = 1/12, alpha = 0.7) +
  geom_stratum(width = 1/12, fill = "white", color = "grey") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 3) +
  scale_x_discrete(limits = c("Overall", "Rep 1", "Rep 2"), expand = c(.05, .05)) +
  scale_fill_manual(values = c("low" = "#ffb300", "medium" = "#00897b", "high" = "#e53935")) +
  labs(title = "Fat Preference Flow: Overall → Rep 1 → Rep 2",
       y = "Number of Participants",
       fill = "Fat Preference") +
  theme_minimal() +
  theme(legend.position = "right")
Warning in to_lodes_form(data = data, axes = axis_ind, discern =
params$discern): Some strata appear at multiple axes.
Warning in to_lodes_form(data = data, axes = axis_ind, discern =
params$discern): Some strata appear at multiple axes.
Warning in to_lodes_form(data = data, axes = axis_ind, discern =
params$discern): Some strata appear at multiple axes.

Code
## Sweet preference flow: sweetPref → sweetPref.1 → sweetPref.2
sweet_flow <- pref.df %>%
  select(ID, sweetPref, sweetPref.1, sweetPref.2) %>%
  count(sweetPref, sweetPref.1, sweetPref.2) %>%
  filter(!is.na(sweetPref) & !is.na(sweetPref.1) & !is.na(sweetPref.2))

ggplot(sweet_flow, 
       aes(axis1 = sweetPref, axis2 = sweetPref.1, axis3 = sweetPref.2, y = n)) +
  geom_alluvium(aes(fill = sweetPref), width = 1/12, alpha = 0.7) +
  geom_stratum(width = 1/12, fill = "white", color = "grey") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 3) +
  scale_x_discrete(limits = c("Overall", "Rep 1", "Rep 2"), expand = c(.05, .05)) +
  scale_fill_manual(values = c("low" = "#FFCA28", "high" = "#F44336")) +
  labs(title = "Sweet Preference Flow: Overall → Rep 1 → Rep 2",
       y = "Number of Participants",
       fill = "Sweet Preference") +
  theme_minimal() +
  theme(legend.position = "right")
Warning in to_lodes_form(data = data, axes = axis_ind, discern =
params$discern): Some strata appear at multiple axes.
Warning in to_lodes_form(data = data, axes = axis_ind, discern =
params$discern): Some strata appear at multiple axes.
Warning in to_lodes_form(data = data, axes = axis_ind, discern =
params$discern): Some strata appear at multiple axes.

Dose response - liking

Code
## Make sweet liking dose dataframe
sweet.liking.dose <- oatmilk.liking.long %>%
  group_by(sample, sweetPref) %>%
  summarize(mean = mean(liking), 
            sd = sd(liking),
            n = n(),           
            sem = sd/sqrt(n)) 
`summarise()` has grouped output by 'sample'. You can override using the
`.groups` argument.
Code
sweet.liking.dose <- sweet.liking.dose %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2)  

sweet.liking.dose$fat.level <- factor(sweet.liking.dose$fat.level , levels = c("F0", "F1", "F2", "F3"))
sweet.liking.dose$sugar.level <- factor(sweet.liking.dose$sugar.level , levels = c("S0", "S1", "S2"))

sweet.liking.dose$sweetPref <- factor(sweet.liking.dose$sweetPref , levels = c("Low", "High"))

## sweet liking by sweet preference
sweet.liking.dose %>%
  filter(!sugar.level %in% "S0") %>%
  filter(!fat.level %in% "F0") %>%
  ggplot(aes(x = sugar.level, y = mean, group = sweetPref, color = sweetPref)) +
  geom_line()+
  geom_hline(yintercept = 50, linetype = "dashed", color = "gray50") + 
  geom_point() +
  scale_color_manual(values = c("#00897b",  "#F44336"), name = "Sweet Preference") +
  geom_errorbar(aes(ymin = mean - sem, ymax = mean + sem), width = 0.2) +
  labs(y = "Liking") +
  facet_wrap(~fat.level) +
  ylim(0, 100) +
  theme_classic() 

Code
## Make fat liking dose dataframe
fat.liking.dose <- oatmilk.liking.long %>%
  group_by(sample, fatPref) %>%
  summarize(mean = mean(liking), 
            sd = sd(liking),
            n = n(),           
            sem = sd/sqrt(n)) 
`summarise()` has grouped output by 'sample'. You can override using the
`.groups` argument.
Code
fat.liking.dose <- fat.liking.dose %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2)  

fat.liking.dose$fatPref <- factor(fat.liking.dose$fatPref , levels = c("Low", "Medium", "High"))

## fat liking by fat preference
fat.liking.dose %>%
  filter(!sugar.level %in% "S0") %>%
  filter(!fat.level %in% "F0") %>%
  ggplot(aes(x = fat.level, y = mean, group = fatPref, color = fatPref)) +
  geom_line()+
  geom_hline(yintercept = 50, linetype = "dashed", color = "gray50") + 
  geom_point() +
  scale_color_manual(values = c("#00897b", "#ffb300",  "#F44336"), name = "Fat Preference") +
  geom_errorbar(aes(ymin = mean - sem, ymax = mean + sem), width = 0.2) +
  labs(y = "Liking") +
  facet_wrap(~sugar.level) +
  ylim(0, 100) +
  theme_classic() 

Code
## By individual
oatmilk.liking.long %>%
  group_by(ID, sample) %>%
    filter(sample != "S0F0") %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2)  %>%
  
  ggplot(aes(x = fat.level, y = liking, group = sugar.level, color = sugar.level)) +
  geom_point() +
  geom_line() +
  labs(y = "Liking") +
  scale_color_manual(values = c("#FFCA28", "#F44336")) +
  facet_wrap(~ID)+
  theme_classic()

Dose response - sweet

Code
## Make sweet liking dose dataframe for sweet intensity
sweetPref.sweet.dose <- oatmilk.sweet.long %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2) %>%
  select(-fatPref) %>%
  group_by(sugar.level, sweetPref) %>%
  summarize(mean = mean(sweet), 
            sd = sd(sweet) ,
            n = n(),           
            sem = sd/sqrt(n)) 
`summarise()` has grouped output by 'sugar.level'. You can override using the
`.groups` argument.
Code
sweetPref.sweet.dose$sugar.level <- factor(sweetPref.sweet.dose$sugar.level, levels = c("S0", "S1", "S2"))

## Testing the difference in sweet intensity perception between sweet liking phenotypes
sweetint.sweetPref.aov <- oatmilk.sweet.long %>%
    separate(sample, into = c("sugar.level", "fat.level"), sep = 2) %>%
  aov(sweet ~ sweetPref*sugar.level, .)
summary(sweetint.sweetPref.aov)
                        Df Sum Sq Mean Sq F value  Pr(>F)    
sweetPref                1   6270    6270  16.872 4.2e-05 ***
sugar.level              2 583372  291686 784.938 < 2e-16 ***
sweetPref:sugar.level    2   1630     815   2.193   0.112    
Residuals             1614 599768     372                    
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
sweetint.sweetPref.emm <- emmeans(sweetint.sweetPref.aov, ~ sweetPref | sugar.level)
sweetint.sweetPref.pairwise <- pairs(sweetint.sweetPref.emm, adjust = "tukey") %>%
  as.data.frame()

# Prepare significance annotations
sig_data <- sweetint.sweetPref.pairwise %>%
  mutate(p.signif = case_when(p.value < 0.001 ~ "***", p.value < 0.01 ~ "**", p.value < 0.05 ~ "*", TRUE ~ "ns")) %>%
  filter(p.value < 0.05)  # Keep only significant comparisons

# Get max y value for positioning asterisks
max_y <- max(sweetPref.sweet.dose$mean + sweetPref.sweet.dose$sem, na.rm = TRUE)

# Add y position for each sugar level
sig_data <- sig_data %>%
  mutate(y.position = max_y + 5)  # Adjust height as needed

## Sweetness intensity dose response by sweetness preference
sweetPref.sweet.dose %>%
  ggplot(aes(x = sugar.level, y = mean, group = sweetPref, color = sweetPref, shape = sweetPref)) +
  geom_line()+
  geom_point() +
  scale_color_manual(values = c("#FFCA28", "#F44336")) +
  geom_errorbar(aes(ymin = mean - sem, ymax = mean + sem), width = 0.05) +
    geom_text(data = sig_data, aes(x = sugar.level, y = y.position, label = p.signif), color = "black", size = 5, inherit.aes = FALSE) +
  labs(y = "Sweetness intensity (0 - 100)") +
  ylim(0, 100) +
  theme_classic()

Code
## Make fat liking dose dataframe for sweet intensity
fatPref.creamy.dose <- oatmilk.creamy.long %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2) %>%
  select(-sweetPref) %>%
  group_by(fat.level, fatPref) %>%
  summarize(mean = mean(creamy), 
            sd = sd(creamy),
            n = n(),           
            sem = sd/sqrt(n)) 
`summarise()` has grouped output by 'fat.level'. You can override using the
`.groups` argument.
Code
fatPref.creamy.dose$fat.level <- factor(fatPref.creamy.dose$fat.level, levels = c("F0", "F1", "F2", "F3"))

## Testing the difference in fat intensity perception between fat liking phenotypes
fatint.fatPref.aov <- oatmilk.creamy.long %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2) %>%
  aov(creamy ~ fatPref*fat.level, .)

summary(fatint.fatPref.aov)
                    Df Sum Sq Mean Sq F value   Pr(>F)    
fatPref              2   3916    1958   8.640 0.000185 ***
fat.level            3 208473   69491 306.659  < 2e-16 ***
fatPref:fat.level    6   3111     519   2.288 0.033311 *  
Residuals         1608 364385     227                     
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
fatint.fatPref.emm <- emmeans(fatint.fatPref.aov, ~ fatPref | fat.level)
fatint.fatPref.pairwise <- pairs(fatint.fatPref.emm, adjust = "tukey") %>%
  as.data.frame()

# Prepare significance annotations
sig_data <- fatint.fatPref.pairwise %>%
  mutate(p.signif = case_when(p.value < 0.001 ~ "***", 
                               p.value < 0.01 ~ "**", 
                               p.value < 0.05 ~ "*", 
                               TRUE ~ "ns")) %>%
  filter(p.value < 0.05)  # Keep only significant comparisons

# Get max y value for positioning asterisks
max_y <- max(fatPref.creamy.dose$mean + fatPref.creamy.dose$sem, na.rm = TRUE)

# Add y position for each fat level
sig_data <- sig_data %>%
  mutate(y.position = max_y + 5)  # Adjust height as needed

## Fattiness intensity dose response by fattiness preference
fatPref.creamy.dose %>%
  ggplot(aes(x = fat.level, y = mean, group = fatPref, color = fatPref, shape = fatPref)) +
  geom_line() +
  geom_point() +
  scale_color_manual(values = c("#FFCA28", "#F44336", "pink")) +  # Adjusted for 3 levels if needed
  geom_errorbar(aes(ymin = mean - sem, ymax = mean + sem), width = 0.05) +
  geom_text(data = sig_data, aes(x = fat.level, y = y.position, label = p.signif), 
            color = "black", size = 5, inherit.aes = FALSE) +
  labs(y = "Creaminess intensity (0 - 100)",
       x = "Fat Level") +
  ylim(0, 100) +
  theme_classic()

Dose response - creamy

Code
creamy.dose <- oatmilk.creamy.long %>%
  group_by(sample) %>%
  summarize(mean = mean(creamy), 
            sd = sd(creamy) ,
            n = n(),           
            sem = sd/sqrt(n)) 

creamy.dose <- creamy.dose %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2)  

creamy.dose$fat.level <- factor(creamy.dose$fat.level , levels = c("F0", "F1", "F2", "F3"))
creamy.dose$sugar.level <- factor(creamy.dose$sugar.level , levels = c("S0", "S1", "S2"))

## Overall
creamy.dose %>%
  filter(sugar.level != "S0") %>%
  ggplot(aes(x = fat.level, y = mean, group = sugar.level, color = sugar.level, shape = sugar.level)) +
  geom_line()+
  geom_point() +
  scale_color_manual(values = c("#FFCA28", "#F44336")) +
  geom_errorbar(aes(ymin = mean - sem, ymax = mean + sem), width = 0.05) +
  labs(y = "Creamy") +
  ylim(0, 100) +
  theme_classic()

Code
## By individual
oatmilk.creamy.long %>%
  group_by(ID, sample) %>%
    filter(sample != "S0F0") %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2)  %>%
  ggplot(aes(x = fat.level, y = creamy, group = sugar.level, color = sugar.level)) +
  geom_point() +
  geom_line() +
  scale_color_manual(values = c("#FFCA28", "#F44336")) +
  facet_wrap(~ID)+
  theme_classic()

Dose response - bitter

Code
bitter.dose <- oatmilk.bitter.long %>%
  group_by(sample) %>%
  summarize(mean = mean(bitter), 
            sd = sd(bitter) ,
            n = n(),           
            sem = sd/sqrt(n)) 

bitter.dose <- bitter.dose %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2)  

bitter.dose$fat.level <- factor(bitter.dose$fat.level , levels = c("F0", "F1", "F2", "F3"))
bitter.dose$sugar.level <- factor(bitter.dose$sugar.level , levels = c("S0", "S1", "S2"))

## Overall
bitter.dose %>%
  filter(sugar.level != "S0") %>%
  ggplot(aes(x = fat.level, y = mean, group = sugar.level, color = sugar.level, shape = sugar.level)) +
  geom_line()+
  geom_point() +
  scale_color_manual(values = c("#FFCA28", "#F44336")) +
  geom_errorbar(aes(ymin = mean - sem, ymax = mean + sem), width = 0.05) +
  labs(y = "Bitter") +
  ylim(-10, 100) +
  theme_classic()

Code
## By individual
oatmilk.bitter.long %>%
  group_by(ID, sample) %>%
    filter(sample != "S0F0") %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2)  %>%
  ggplot(aes(x = fat.level, y = bitter, group = sugar.level, color = sugar.level)) +
  geom_point() +
  geom_line() +
  scale_color_manual(values = c("#FFCA28", "#F44336")) +
  facet_wrap(~ID)+
  theme_classic()

Corrplot - all

Code
## FDR adjustment
adjust.cor.pmat <- function(p.mat, method = "fdr") {
  p.mat[upper.tri(p.mat)] <- p.adjust(p.mat[upper.tri(p.mat)], method = method)
  p.mat[lower.tri(p.mat)] <- t(p.mat)[lower.tri(p.mat)]
  diag(p.mat) <- 0
  return(p.mat)
}

## survey corr
    ## other variables to potentially add to the corrplot (liking_S0F0, liking_S1F0, liking_S1F1, liking_S1F2, liking_S1F3, liking_S2F0, liking_S2F1, liking_S2F2, liking_S2F3, sweetliking.f0, sweetliking.f1, sweetliking.f2, sweetliking.f3)

all.corr.df <- full.df %>%
  select(age, BMI, WC, hinc, restraint, emotional, uncontrolled, sfbl.liking, plantmilk_freq, sugar.intake, sHEI, lean_mass, SMM, FFM, SMM_wt, trunk_lean_mass, BFM, PBF, trunk_fat_mass, visceral_fat, BMR, sweetpref.atF2, sweetpref.atF3, fatpref.atS1, pref.cal) %>%
  mutate(across(everything(), as.numeric)) %>%
  rename("household income" = hinc, "sugar intake" = sugar.intake, 
         "healthy eating index" = sHEI, "sweet foods liking" = sfbl.liking) 

all.corr <- all.corr.df %>%
      cor(use = "complete.obs")

p.mat <- cor_pmat(all.corr.df) %>%
  column_to_rownames()
p.mat.adj <- adjust.cor.pmat(p.mat, method = "fdr")

ggcorrplot(all.corr, type = "lower", p.mat = p.mat, insig = "blank", lab = TRUE, lab_size = 2.5, colors = c("#E46726", "white", "#6D9EC1")) 
No id variables; using all as measure variables

Code
ggcorrplot(all.corr, type = "lower", p.mat = p.mat.adj, insig = "blank", lab = TRUE, lab_size = 2.5, colors = c("#E46726", "white", "#6D9EC1")) + ggtitle("FDR adjusted")
No id variables; using all as measure variables

Partial correlation

Code
# Step 1: Prepare data
all.corr.df <- full.df %>%
  select(age, plantmilk_freq, BMI, WC, hinc, restraint, emotional, uncontrolled, 
         sfbl.liking, sugar.intake, sHEI, lean_mass, SMM, FFM, SMM_wt, 
         trunk_lean_mass, BFM, PBF, trunk_fat_mass, visceral_fat, BMR, sweetpref.atF2, fatpref.atS1, pref.cal) %>%
  mutate(across(everything(), as.numeric)) %>%
  rename("household income" = hinc, "sugar intake" = sugar.intake, 
         "healthy eating index" = sHEI, "sweet foods liking" = sfbl.liking, "sweet preference" = sweetpref.atF2, "fat preference" = fatpref.atS1)

# Variables of interest (excluding both covariates)
vars_of_interest <- c("BMI", "WC", "household income", "restraint", "emotional", 
                      "uncontrolled", "sweet foods liking", "sugar intake", 
                      "healthy eating index", "lean_mass", "SMM", "FFM", "SMM_wt", 
                      "trunk_lean_mass", "BFM", "PBF", "trunk_fat_mass", 
                      "visceral_fat", "BMR", "sweet preference", "fat preference", "pref.cal")

# Combine with BOTH control variables
all_vars <- c(vars_of_interest, "age", "plantmilk_freq")
data_subset <- all.corr.df[, all_vars]

# Compute correlation matrix with pairwise deletion
cor_matrix <- cor(data_subset, use = "pairwise.complete.obs")

# Compute partial correlations from the correlation matrix
partial_cor_full <- cor2pcor(cor_matrix)

# Extract just the correlations among your variables of interest
# (exclude the last 2 rows/columns which are age and plantmilk_freq)
n_vars <- length(vars_of_interest)
partial_cor_matrix <- partial_cor_full[1:n_vars, 1:n_vars]

# Add variable names
rownames(partial_cor_matrix) <- vars_of_interest
colnames(partial_cor_matrix) <- vars_of_interest

# Updated function to compute p-values with TWO control variables
compute_partial_cor_pvalues_2covs <- function(data, vars_interest, control_vars) {
  n_vars <- length(vars_interest)
  p_matrix <- matrix(1, nrow = n_vars, ncol = n_vars)
  
  for (i in 1:(n_vars-1)) {
    for (j in (i+1):n_vars) {
      # Get complete cases for this specific set of variables (2 vars + 2 controls)
      subset_data <- data[, c(vars_interest[i], vars_interest[j], control_vars)]
      subset_complete <- na.omit(subset_data)
      
      if (nrow(subset_complete) > 4) {  # Need at least 5 observations for 2 covariates
        # Compute partial correlation for this pair, controlling for BOTH covariates
        pcor_result <- pcor.test(subset_complete[,1], subset_complete[,2], 
                                 subset_complete[, 3:4])  # Both control variables
        p_matrix[i, j] <- pcor_result$p.value
        p_matrix[j, i] <- pcor_result$p.value
      }
    }
  }
  
  return(p_matrix)
}

# Compute p-values (this may take a moment)
p_values <- compute_partial_cor_pvalues_2covs(data_subset, vars_of_interest, 
                                               c("age", "plantmilk_freq"))
rownames(p_values) <- vars_of_interest
colnames(p_values) <- vars_of_interest

# Apply FDR correction
lower_tri_indices <- lower.tri(p_values)
p_values_vector <- p_values[lower_tri_indices]
p_adjusted <- p.adjust(p_values_vector, method = "fdr")

# Create adjusted p-value matrix
p_adjusted_matrix <- matrix(1, nrow = n_vars, ncol = n_vars)
p_adjusted_matrix[lower_tri_indices] <- p_adjusted
p_adjusted_matrix <- t(p_adjusted_matrix)
p_adjusted_matrix[lower_tri_indices] <- p_adjusted
diag(p_adjusted_matrix) <- 0

rownames(p_adjusted_matrix) <- vars_of_interest
colnames(p_adjusted_matrix) <- vars_of_interest

# Plot
ggcorrplot(partial_cor_matrix, 
           type = "lower", 
           p.mat = p_adjusted_matrix, 
           insig = "blank", 
           lab = TRUE, 
           lab_size = 2.5, 
           colors = c("#E46726", "white", "#6D9EC1"),
           title = "Partial Correlations (controlling for age and plantmilk_freq)")

Group difference - demographics

Code
## Age
sweet.age.aov <- full.df %>%
  aov(age ~ sweetPref , .)
summary(sweet.age.aov)
             Df Sum Sq Mean Sq F value Pr(>F)
sweetPref     1    2.5    2.54   0.243  0.622
Residuals   178 1858.4   10.44               
Code
summary(emmeans(sweet.age.aov, ~ sweetPref))
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         21.3 0.511 178     20.3     22.3
 High        21.6 0.273 178     21.0     22.1

Confidence level used: 0.95 
Code
fat.age.aov <- full.df %>%
  aov(age ~ fatPref , .)
summary(fat.age.aov)
             Df Sum Sq Mean Sq F value Pr(>F)
fatPref       2      5   2.499   0.238  0.788
Residuals   177   1856  10.485               
Code
summary(emmeans(fat.age.aov, ~ fatPref))
 fatPref emmean    SE  df lower.CL upper.CL
 Low       21.6 0.477 177     20.7     22.6
 Medium    21.3 0.387 177     20.6     22.1
 High      21.7 0.405 177     20.9     22.5

Confidence level used: 0.95 
Code
## Education
sweet.edu.aov <- full.df %>%
  aov(education ~ sweetPref , .)
summary(sweet.edu.aov)
             Df Sum Sq Mean Sq F value Pr(>F)
sweetPref     1    2.5   2.477   0.966  0.327
Residuals   178  456.5   2.565               
Code
summary(emmeans(sweet.edu.aov, ~ sweetPref))
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         6.67 0.253 178     6.18     7.17
 High        6.96 0.135 178     6.69     7.22

Confidence level used: 0.95 
Code
fat.edu.aov <- full.df %>%
  aov(education ~ fatPref , .)
summary(fat.edu.aov)
             Df Sum Sq Mean Sq F value Pr(>F)
fatPref       2    1.6  0.7783   0.301   0.74
Residuals   177  457.4  2.5844               
Code
summary(emmeans(fat.edu.aov, ~ fatPref))
 fatPref emmean    SE  df lower.CL upper.CL
 Low       6.91 0.237 177     6.45     7.38
 Medium    6.79 0.192 177     6.41     7.16
 High      7.00 0.201 177     6.60     7.40

Confidence level used: 0.95 
Code
## Household income
sweet.hinc.aov <- full.df %>%
  aov(hinc ~ sweetPref , .)
summary(sweet.hinc.aov)
             Df Sum Sq Mean Sq F value Pr(>F)
sweetPref     1    3.1   3.073   0.902  0.343
Residuals   178  606.3   3.406               
Code
summary(emmeans(sweet.hinc.aov, ~ sweetPref))
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         4.55 0.292 178     3.97     5.13
 High        4.86 0.156 178     4.56     5.17

Confidence level used: 0.95 
Code
fat.hinc.aov <- full.df %>%
  aov(hinc ~ fatPref , .)
summary(fat.hinc.aov)
             Df Sum Sq Mean Sq F value Pr(>F)
fatPref       2    2.4   1.191   0.347  0.707
Residuals   177  607.0   3.429               
Code
summary(emmeans(fat.hinc.aov, ~ fatPref))
 fatPref emmean    SE  df lower.CL upper.CL
 Low       4.93 0.273 177     4.40     5.47
 Medium    4.66 0.221 177     4.22     5.09
 High      4.84 0.231 177     4.39     5.30

Confidence level used: 0.95 
Code
## PB-milk frequency
sweet.pbmilk.aov <- full.df %>%
  aov(plantmilk_freq ~ sweetPref , .)
summary(sweet.pbmilk.aov)
             Df Sum Sq Mean Sq F value Pr(>F)  
sweetPref     1   16.7  16.677   5.469 0.0205 *
Residuals   178  542.8   3.049                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
summary(emmeans(sweet.pbmilk.aov, ~ sweetPref))
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         3.62 0.276 178     3.08     4.17
 High        2.89 0.148 178     2.60     3.18

Confidence level used: 0.95 
Code
fat.pbmilk.aov <- full.df %>%
  aov(plantmilk_freq ~ fatPref , .)
summary(fat.pbmilk.aov)
             Df Sum Sq Mean Sq F value  Pr(>F)   
fatPref       2   35.9  17.926    6.06 0.00285 **
Residuals   177  523.6   2.958                   
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
summary(emmeans(fat.pbmilk.aov, ~ fatPref))
 fatPref emmean    SE  df lower.CL upper.CL
 Low       2.74 0.254 177     2.24     3.24
 Medium    2.71 0.206 177     2.31     3.12
 High      3.66 0.215 177     3.23     4.08

Confidence level used: 0.95 

Group difference, pref.cal, diet

Code
## sHEI
sHEI.aov <- full.df %>%
  aov(sHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(sHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)
as.factor(prefcal.cat)   2     63   31.33   0.397  0.673
age                      1    126  125.77   1.594  0.208
plantmilk_freq           1     55   55.00   0.697  0.405
Residuals              175  13811   78.92               
Code
## Total fruit HEI
tfuitHEI.aov <- full.df %>%
  aov(tfruitHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(tfuitHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)
as.factor(prefcal.cat)   2   18.1   9.039   1.693  0.187
age                      1    0.0   0.002   0.000  0.987
plantmilk_freq           1    2.2   2.227   0.417  0.519
Residuals              175  934.6   5.340               
Code
## Whole fruit HEI
wfruitHEI.aov <- full.df %>%
  aov(wfruitHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(wfruitHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)
as.factor(prefcal.cat)   2    4.4   2.221   0.584  0.559
age                      1    0.0   0.008   0.002  0.963
plantmilk_freq           1    6.6   6.630   1.744  0.188
Residuals              175  665.1   3.801               
Code
## Veg fruit HEI
vegHEI.aov <- full.df %>%
  aov(vegHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(vegHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2   4.76  2.3782   3.875 0.0226 *
age                      1   1.20  1.1960   1.949 0.1645  
plantmilk_freq           1   1.66  1.6630   2.710 0.1015  
Residuals              175 107.40  0.6137                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
emmeans(vegHEI.aov, pairwise ~ prefcal.cat, adjust = "tukey")
$emmeans
 prefcal.cat emmean     SE  df lower.CL upper.CL
 1             2.44 0.0996 175     2.25     2.64
 2             2.70 0.0988 175     2.50     2.89
 3             2.85 0.1060 175     2.64     3.05

Confidence level used: 0.95 

$contrasts
 contrast                    estimate    SE  df t.ratio p.value
 prefcal.cat1 - prefcal.cat2   -0.254 0.140 175  -1.808  0.1700
 prefcal.cat1 - prefcal.cat3   -0.403 0.145 175  -2.777  0.0167
 prefcal.cat2 - prefcal.cat3   -0.149 0.145 175  -1.032  0.5578

P value adjustment: tukey method for comparing a family of 3 estimates 
Code
emmeans(vegHEI.aov, ~prefcal.cat)
 prefcal.cat emmean     SE  df lower.CL upper.CL
 1             2.44 0.0996 175     2.25     2.64
 2             2.70 0.0988 175     2.50     2.89
 3             2.85 0.1060 175     2.64     3.05

Confidence level used: 0.95 
Code
## Bean HEI
beanHEI.aov <- full.df %>%
  aov(beanHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(beanHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2   20.9  10.467   2.692 0.0705 .
age                      1   10.2  10.215   2.627 0.1068  
plantmilk_freq           1    8.5   8.473   2.179 0.1417  
Residuals              175  680.4   3.888                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
## Wg HEI
wgHEI.aov <- full.df %>%
  aov(wgHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(wgHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2    7.2   3.605   0.737 0.4798  
age                      1   14.8  14.751   3.018 0.0841 .
plantmilk_freq           1   17.6  17.647   3.610 0.0591 .
Residuals              175  855.4   4.888                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
## Dairy HEI
dairyHEI.aov <- full.df %>%
  aov(dairyHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(dairyHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2   8.17   4.087   2.826  0.062 .
age                      1   0.32   0.323   0.223  0.637  
plantmilk_freq           1   1.80   1.797   1.242  0.267  
Residuals              175 253.10   1.446                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
## Total protein HEI
tproteinHEI.aov <- full.df %>%
  aov(tproteinHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(tproteinHEI.aov)
                        Df    Sum Sq   Mean Sq F value Pr(>F)
as.factor(prefcal.cat)   2 1.920e-29 9.625e-30   0.944  0.391
age                      1 4.900e-30 4.935e-30   0.484  0.488
plantmilk_freq           1 2.000e-30 2.019e-30   0.198  0.657
Residuals              175 1.784e-27 1.020e-29               
Code
## SF protein HEI
sfpproteinHEI.aov <- full.df %>%
  aov(sfpproteinHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(sfpproteinHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)
as.factor(prefcal.cat)   2   0.95  0.4733   0.618  0.540
age                      1   0.00  0.0034   0.004  0.947
plantmilk_freq           1   0.18  0.1762   0.230  0.632
Residuals              175 134.10  0.7663               
Code
## Fat HEI
fatHEI.aov <- full.df %>%
  aov(fatHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(fatHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2   4.63   2.315   1.341  0.264  
age                      1   2.38   2.381   1.379  0.242  
plantmilk_freq           1   5.35   5.354   3.100  0.080 .
Residuals              175 302.20   1.727                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
## Grain HEI
grainHEI.aov <- full.df %>%
  aov(grainHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(grainHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)
as.factor(prefcal.cat)   2    8.1   4.034   0.630  0.534
age                      1    7.3   7.348   1.148  0.286
plantmilk_freq           1    0.7   0.742   0.116  0.734
Residuals              175 1120.6   6.403               
Code
## Sodium HEI
sodiumHEI.aov <- full.df %>%
  aov(sodiumHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(sodiumHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2   28.4  14.189   3.501 0.0323 *
age                      1    7.6   7.588   1.872 0.1730  
plantmilk_freq           1    6.1   6.102   1.505 0.2215  
Residuals              175  709.4   4.054                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
emmeans(sodiumHEI.aov, pairwise ~ prefcal.cat, adjust = "tukey")
$emmeans
 prefcal.cat emmean    SE  df lower.CL upper.CL
 1             4.07 0.256 175     3.56     4.57
 2             3.21 0.254 175     2.70     3.71
 3             3.23 0.271 175     2.69     3.76

Confidence level used: 0.95 

$contrasts
 contrast                    estimate    SE  df t.ratio p.value
 prefcal.cat1 - prefcal.cat2   0.8612 0.361 175   2.386  0.0473
 prefcal.cat1 - prefcal.cat3   0.8404 0.373 175   2.252  0.0655
 prefcal.cat2 - prefcal.cat3  -0.0208 0.372 175  -0.056  0.9983

P value adjustment: tukey method for comparing a family of 3 estimates 
Code
emmeans(sodiumHEI.aov, ~ prefcal.cat)
 prefcal.cat emmean    SE  df lower.CL upper.CL
 1             4.07 0.256 175     3.56     4.57
 2             3.21 0.254 175     2.70     3.71
 3             3.23 0.271 175     2.69     3.76

Confidence level used: 0.95 
Code
## Sugar HEI
sugarHEI.aov <- full.df %>%
  aov(sugarHEI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(sugarHEI.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)
as.factor(prefcal.cat)   2   15.7   7.862   1.083  0.341
age                      1    8.7   8.731   1.203  0.274
plantmilk_freq           1   10.3  10.337   1.424  0.234
Residuals              175 1270.1   7.258               
Code
## Sugar intake
sugarintake.aov <- full.df %>%
  aov(sugar.intake ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(sugarintake.aov)
                        Df   Sum Sq Mean Sq F value Pr(>F)
as.factor(prefcal.cat)   2   145382   72691   1.048  0.353
age                      1      759     759   0.011  0.917
plantmilk_freq           1    38909   38909   0.561  0.455
Residuals              175 12135947   69348               

Group difference, 2x2 ANCOVA, diet

Code
## sHEI
sHEI.lm <- full.df %>%
  filter(!is.na(sHEI) & !is.na(sweetPref) & !is.na(fatPref) & !is.na(age)) %>%
  lm(sHEI ~ sweetPref*fatPref + age + plantmilk_freq, data = .)
summary(sHEI.lm)

Call:
lm(formula = sHEI ~ sweetPref * fatPref + age + plantmilk_freq, 
    data = .)

Residuals:
     Min       1Q   Median       3Q      Max 
-24.7446  -5.2134   0.8743   5.5194  19.5429 

Coefficients:
                            Estimate Std. Error t value Pr(>|t|)    
(Intercept)                  45.3512     4.9849   9.098 2.24e-16 ***
sweetPrefHigh                -7.2261     2.9492  -2.450   0.0153 *  
fatPrefMedium                -2.5981     3.2270  -0.805   0.4219    
fatPrefHigh                   0.3501     3.7795   0.093   0.9263    
age                           0.2653     0.2014   1.317   0.1896    
plantmilk_freq               -0.1832     0.3867  -0.474   0.6363    
sweetPrefHigh:fatPrefMedium   1.5198     3.7335   0.407   0.6845    
sweetPrefHigh:fatPrefHigh     3.5190     4.1710   0.844   0.4000    
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 8.512 on 172 degrees of freedom
Multiple R-squared:  0.1133,    Adjusted R-squared:  0.07721 
F-statistic: 3.139 on 7 and 172 DF,  p-value: 0.003804
Code
summary.aov(sHEI.lm)
                   Df Sum Sq Mean Sq F value  Pr(>F)   
sweetPref           1    708   707.9   9.770 0.00208 **
fatPref             2    686   342.9   4.733 0.00998 **
age                 1    125   125.1   1.727 0.19055   
plantmilk_freq      1     21    21.4   0.296 0.58736   
sweetPref:fatPref   2     52    26.0   0.359 0.69909   
Residuals         172  12462    72.5                   
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
confint(sHEI.lm)
                                  2.5 %     97.5 %
(Intercept)                  35.5118022 55.1906490
sweetPrefHigh               -13.0473953 -1.4048331
fatPrefMedium                -8.9676724  3.7714480
fatPrefHigh                  -7.1101133  7.8103012
age                          -0.1322946  0.6628148
plantmilk_freq               -0.9465693  0.5801216
sweetPrefHigh:fatPrefMedium  -5.8496969  8.8892384
sweetPrefHigh:fatPrefHigh    -4.7140619 11.7519991
Code
eta_squared(sHEI.lm)
        sweetPref           fatPref               age    plantmilk_freq 
      0.050368944       0.048797627       0.008903117       0.001523876 
sweetPref:fatPref 
      0.003698606 
Code
emmeans(sHEI.lm, pairwise ~ sweetPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         49.8 1.430 172     46.9     52.6
 High        44.2 0.737 172     42.7     45.7

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 

$contrasts
 contrast   estimate   SE  df t.ratio p.value
 Low - High     5.55 1.62 172   3.423  0.0008

Results are averaged over the levels of: fatPref 
Code
emmeans(sHEI.lm, ~sweetPref)
NOTE: Results may be misleading due to involvement in interactions
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         49.8 1.430 172     46.9     52.6
 High        44.2 0.737 172     42.7     45.7

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 
Code
emmeans(sHEI.lm, pairwise ~ fatPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 fatPref emmean   SE  df lower.CL upper.CL
 Low       46.9 1.47 172     44.0     49.8
 Medium    45.0 1.15 172     42.8     47.3
 High      49.0 1.52 172     46.0     52.0

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 

$contrasts
 contrast      estimate   SE  df t.ratio p.value
 Low - Medium      1.84 1.86 172   0.986  0.5865
 Low - High       -2.11 2.13 172  -0.989  0.5848
 Medium - High    -3.95 1.91 172  -2.062  0.1010

Results are averaged over the levels of: sweetPref 
P value adjustment: tukey method for comparing a family of 3 estimates 
Code
emmeans(sHEI.lm, ~fatPref)
NOTE: Results may be misleading due to involvement in interactions
 fatPref emmean   SE  df lower.CL upper.CL
 Low       46.9 1.47 172     44.0     49.8
 Medium    45.0 1.15 172     42.8     47.3
 High      49.0 1.52 172     46.0     52.0

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 
Code
## Total fruit HEI
tfuitHEI.lm <- full.df %>%
  lm(tfruitHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(tfuitHEI.lm)

Call:
lm(formula = tfruitHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
   Min     1Q Median     3Q    Max 
-2.517 -1.731 -1.267  2.857  4.019 

Coefficients:
                                                   Estimate Std. Error t value
(Intercept)                                        2.313643   1.356879   1.705
as.factor(sweetPref)High                          -1.274319   0.802768  -1.587
as.factor(fatPref)Medium                          -0.692146   0.878377  -0.788
as.factor(fatPref)High                             0.233268   1.028780   0.227
age                                               -0.001277   0.054824  -0.023
plantmilk_freq                                    -0.004411   0.105267  -0.042
as.factor(sweetPref)High:as.factor(fatPref)Medium  0.965272   1.016266   0.950
as.factor(sweetPref)High:as.factor(fatPref)High    0.529895   1.135354   0.467
                                                  Pr(>|t|)  
(Intercept)                                          0.090 .
as.factor(sweetPref)High                             0.114  
as.factor(fatPref)Medium                             0.432  
as.factor(fatPref)High                               0.821  
age                                                  0.981  
plantmilk_freq                                       0.967  
as.factor(sweetPref)High:as.factor(fatPref)Medium    0.344  
as.factor(sweetPref)High:as.factor(fatPref)High      0.641  
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 2.317 on 172 degrees of freedom
Multiple R-squared:  0.03303,   Adjusted R-squared:  -0.006328 
F-statistic: 0.8392 on 7 and 172 DF,  p-value: 0.5562
Code
summary.aov(tfuitHEI.lm)
                                         Df Sum Sq Mean Sq F value Pr(>F)
as.factor(sweetPref)                      1   11.5  11.468   2.136  0.146
as.factor(fatPref)                        2   15.1   7.565   1.409  0.247
age                                       1    0.0   0.035   0.007  0.936
plantmilk_freq                            1    0.0   0.028   0.005  0.942
as.factor(sweetPref):as.factor(fatPref)   2    4.9   2.436   0.454  0.636
Residuals                               172  923.3   5.368               
Code
## Whole fruit HEI
wfruitHEI.lm <- full.df %>%
  lm(wfruitHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(wfruitHEI.lm)

Call:
lm(formula = wfruitHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
    Min      1Q  Median      3Q     Max 
-3.8645 -1.2484  0.3179  1.5965  2.2142 

Coefficients:
                                                   Estimate Std. Error t value
(Intercept)                                        3.373373   1.135284   2.971
as.factor(sweetPref)High                          -0.530460   0.671666  -0.790
as.factor(fatPref)Medium                          -0.130097   0.734927  -0.177
as.factor(fatPref)High                             0.517749   0.860767   0.601
age                                               -0.004553   0.045870  -0.099
plantmilk_freq                                     0.043023   0.088076   0.488
as.factor(sweetPref)High:as.factor(fatPref)Medium  0.169460   0.850297   0.199
as.factor(sweetPref)High:as.factor(fatPref)High    0.293709   0.949936   0.309
                                                  Pr(>|t|)   
(Intercept)                                        0.00339 **
as.factor(sweetPref)High                           0.43075   
as.factor(fatPref)Medium                           0.85970   
as.factor(fatPref)High                             0.54830   
age                                                0.92105   
plantmilk_freq                                     0.62583   
as.factor(sweetPref)High:as.factor(fatPref)Medium  0.84227   
as.factor(sweetPref)High:as.factor(fatPref)High    0.75755   
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 1.939 on 172 degrees of freedom
Multiple R-squared:  0.04413,   Adjusted R-squared:  0.005233 
F-statistic: 1.135 on 7 and 172 DF,  p-value: 0.3437
Code
summary.aov(wfruitHEI.lm)
                                         Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1    2.9   2.867   0.763 0.3836  
as.factor(fatPref)                        2   25.8  12.900   3.433 0.0345 *
age                                       1    0.0   0.000   0.000 0.9924  
plantmilk_freq                            1    0.8   0.814   0.217 0.6421  
as.factor(sweetPref):as.factor(fatPref)   2    0.4   0.182   0.048 0.9528  
Residuals                               172  646.4   3.758                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
emmeans(wfruitHEI.lm, pairwise ~ fatPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 fatPref emmean    SE  df lower.CL upper.CL
 Low       3.14 0.335 172     2.48     3.80
 Medium    3.10 0.261 172     2.58     3.61
 High      3.81 0.347 172     3.12     4.49

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 

$contrasts
 contrast      estimate    SE  df t.ratio p.value
 Low - Medium    0.0454 0.424 172   0.107  0.9937
 Low - High     -0.6646 0.486 172  -1.368  0.3599
 Medium - High  -0.7100 0.436 172  -1.628  0.2366

Results are averaged over the levels of: sweetPref 
P value adjustment: tukey method for comparing a family of 3 estimates 
Code
emmeans(wfruitHEI.lm, ~fatPref)
NOTE: Results may be misleading due to involvement in interactions
 fatPref emmean    SE  df lower.CL upper.CL
 Low       3.14 0.335 172     2.48     3.80
 Medium    3.10 0.261 172     2.58     3.61
 High      3.81 0.347 172     3.12     4.49

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 
Code
## Veg fruit HEI
vegHEI.lm <- full.df %>%
  lm(vegHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(vegHEI.lm)

Call:
lm(formula = vegHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
     Min       1Q   Median       3Q      Max 
-1.34385 -0.81076 -0.00235  0.69790  1.18155 

Coefficients:
                                                   Estimate Std. Error t value
(Intercept)                                        2.262465   0.463690   4.879
as.factor(sweetPref)High                          -0.281751   0.274332  -1.027
as.factor(fatPref)Medium                           0.043210   0.300170   0.144
as.factor(fatPref)High                             0.238032   0.351568   0.677
age                                                0.020902   0.018735   1.116
plantmilk_freq                                     0.025323   0.035973   0.704
as.factor(sweetPref)High:as.factor(fatPref)Medium -0.067934   0.347292  -0.196
as.factor(sweetPref)High:as.factor(fatPref)High    0.008269   0.387988   0.021
                                                  Pr(>|t|)    
(Intercept)                                       2.41e-06 ***
as.factor(sweetPref)High                             0.306    
as.factor(fatPref)Medium                             0.886    
as.factor(fatPref)High                               0.499    
age                                                  0.266    
plantmilk_freq                                       0.482    
as.factor(sweetPref)High:as.factor(fatPref)Medium    0.845    
as.factor(sweetPref)High:as.factor(fatPref)High      0.983    
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 0.7918 on 172 degrees of freedom
Multiple R-squared:  0.06251,   Adjusted R-squared:  0.02436 
F-statistic: 1.638 on 7 and 172 DF,  p-value: 0.1276
Code
summary.aov(vegHEI.lm)
                                         Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1   2.59  2.5869   4.126 0.0438 *
as.factor(fatPref)                        2   3.24  1.6186   2.582 0.0786 .
age                                       1   1.02  1.0171   1.622 0.2045  
plantmilk_freq                            1   0.31  0.3093   0.493 0.4834  
as.factor(sweetPref):as.factor(fatPref)   2   0.04  0.0197   0.031 0.9691  
Residuals                               172 107.83  0.6269                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
emmeans(vegHEI.lm, pairwise ~ sweetPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 sweetPref emmean     SE  df lower.CL upper.CL
 Low         2.88 0.1330 172     2.62     3.15
 High        2.58 0.0686 172     2.45     2.72

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 

$contrasts
 contrast   estimate    SE  df t.ratio p.value
 Low - High    0.302 0.151 172   2.001  0.0469

Results are averaged over the levels of: fatPref 
Code
emmeans(vegHEI.lm, ~sweetPref)
NOTE: Results may be misleading due to involvement in interactions
 sweetPref emmean     SE  df lower.CL upper.CL
 Low         2.88 0.1330 172     2.62     3.15
 High        2.58 0.0686 172     2.45     2.72

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 
Code
## Bean HEI
beanHEI.lm <- full.df %>%
  lm(beanHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(beanHEI.lm)

Call:
lm(formula = beanHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
    Min      1Q  Median      3Q     Max 
-4.6980  0.0714  0.8874  1.1879  1.7415 

Coefficients:
                                                  Estimate Std. Error t value
(Intercept)                                        2.46151    1.17077   2.102
as.factor(sweetPref)High                          -0.22006    0.69266  -0.318
as.factor(fatPref)Medium                          -0.44937    0.75790  -0.593
as.factor(fatPref)High                             0.83826    0.88768   0.944
age                                                0.06486    0.04730   1.371
plantmilk_freq                                     0.07884    0.09083   0.868
as.factor(sweetPref)High:as.factor(fatPref)Medium  0.36506    0.87688   0.416
as.factor(sweetPref)High:as.factor(fatPref)High   -0.51324    0.97963  -0.524
                                                  Pr(>|t|)  
(Intercept)                                          0.037 *
as.factor(sweetPref)High                             0.751  
as.factor(fatPref)Medium                             0.554  
as.factor(fatPref)High                               0.346  
age                                                  0.172  
plantmilk_freq                                       0.387  
as.factor(sweetPref)High:as.factor(fatPref)Medium    0.678  
as.factor(sweetPref)High:as.factor(fatPref)High      0.601  
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 1.999 on 172 degrees of freedom
Multiple R-squared:  0.04526,   Adjusted R-squared:  0.006399 
F-statistic: 1.165 on 7 and 172 DF,  p-value: 0.3256
Code
summary.aov(beanHEI.lm)
                                         Df Sum Sq Mean Sq F value Pr(>F)
as.factor(sweetPref)                      1    0.8   0.804   0.201  0.654
as.factor(fatPref)                        2   16.2   8.080   2.022  0.136
age                                       1    8.2   8.238   2.061  0.153
plantmilk_freq                            1    3.4   3.383   0.846  0.359
as.factor(sweetPref):as.factor(fatPref)   2    4.0   2.000   0.500  0.607
Residuals                               172  687.4   3.997               
Code
## Wg HEI
wgHEI.lm <- full.df %>%
  lm(wgHEI ~ as.factor(sweetPref)*as.factor(fatPref)+ age + plantmilk_freq, .)
summary(wgHEI.lm)

Call:
lm(formula = wgHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
    Min      1Q  Median      3Q     Max 
-4.7995 -0.1196  0.7162  1.2010  3.3961 

Coefficients:
                                                  Estimate Std. Error t value
(Intercept)                                        2.37012    1.30236   1.820
as.factor(sweetPref)High                           0.27229    0.77052   0.353
as.factor(fatPref)Medium                           0.15844    0.84309   0.188
as.factor(fatPref)High                             0.18002    0.98745   0.182
age                                                0.06502    0.05262   1.236
plantmilk_freq                                     0.15466    0.10104   1.531
as.factor(sweetPref)High:as.factor(fatPref)Medium -0.58205    0.97544  -0.597
as.factor(sweetPref)High:as.factor(fatPref)High    0.08816    1.08974   0.081
                                                  Pr(>|t|)  
(Intercept)                                         0.0705 .
as.factor(sweetPref)High                            0.7242  
as.factor(fatPref)Medium                            0.8512  
as.factor(fatPref)High                              0.8556  
age                                                 0.2183  
plantmilk_freq                                      0.1277  
as.factor(sweetPref)High:as.factor(fatPref)Medium   0.5515  
as.factor(sweetPref)High:as.factor(fatPref)High     0.9356  
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 2.224 on 172 degrees of freedom
Multiple R-squared:  0.04963,   Adjusted R-squared:  0.01095 
F-statistic: 1.283 on 7 and 172 DF,  p-value: 0.2613
Code
summary.aov(wgHEI.lm)
                                         Df Sum Sq Mean Sq F value Pr(>F)
as.factor(sweetPref)                      1    0.0   0.001   0.000  0.987
as.factor(fatPref)                        2   17.6   8.819   1.783  0.171
age                                       1   12.3  12.331   2.493  0.116
plantmilk_freq                            1   11.5  11.466   2.318  0.130
as.factor(sweetPref):as.factor(fatPref)   2    3.0   1.492   0.302  0.740
Residuals                               172  850.6   4.945               
Code
## Dairy HEI
dairyHEI.lm <- full.df %>%
  lm(dairyHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(dairyHEI.lm)

Call:
lm(formula = dairyHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
    Min      1Q  Median      3Q     Max 
-1.8089 -0.8654 -0.6563  0.6468  2.6728 

Coefficients:
                                                  Estimate Std. Error t value
(Intercept)                                        4.67132    0.71025   6.577
as.factor(sweetPref)High                          -0.63170    0.42020  -1.503
as.factor(fatPref)Medium                          -0.81245    0.45978  -1.767
as.factor(fatPref)High                            -0.33619    0.53851  -0.624
age                                                0.02145    0.02870   0.748
plantmilk_freq                                    -0.07871    0.05510  -1.428
as.factor(sweetPref)High:as.factor(fatPref)Medium  0.58808    0.53196   1.106
as.factor(sweetPref)High:as.factor(fatPref)High    0.30992    0.59429   0.521
                                                  Pr(>|t|)    
(Intercept)                                       5.54e-10 ***
as.factor(sweetPref)High                             0.135    
as.factor(fatPref)Medium                             0.079 .  
as.factor(fatPref)High                               0.533    
age                                                  0.456    
plantmilk_freq                                       0.155    
as.factor(sweetPref)High:as.factor(fatPref)Medium    0.270    
as.factor(sweetPref)High:as.factor(fatPref)High      0.603    
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 1.213 on 172 degrees of freedom
Multiple R-squared:  0.03951,   Adjusted R-squared:  0.000421 
F-statistic: 1.011 on 7 and 172 DF,  p-value: 0.4254
Code
summary.aov(dairyHEI.lm)
                                         Df Sum Sq Mean Sq F value Pr(>F)
as.factor(sweetPref)                      1   1.12   1.121   0.762  0.384
as.factor(fatPref)                        2   3.98   1.990   1.353  0.261
age                                       1   0.32   0.325   0.221  0.639
plantmilk_freq                            1   3.16   3.164   2.151  0.144
as.factor(sweetPref):as.factor(fatPref)   2   1.82   0.908   0.617  0.541
Residuals                               172 252.98   1.471               
Code
## Total protein HEI
tproteinHEI.lm <- full.df %>%
  lm(tproteinHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(tproteinHEI.lm)
Warning in summary.lm(tproteinHEI.lm): essentially perfect fit: summary may be
unreliable

Call:
lm(formula = tproteinHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
       Min         1Q     Median         3Q        Max 
-3.859e-14 -1.520e-16 -2.000e-17  1.440e-16  4.142e-15 

Coefficients:
                                                    Estimate Std. Error
(Intercept)                                        4.970e+00  1.812e-15
as.factor(sweetPref)High                           3.871e-15  1.072e-15
as.factor(fatPref)Medium                           3.914e-15  1.173e-15
as.factor(fatPref)High                             3.927e-15  1.374e-15
age                                               -5.617e-17  7.321e-17
plantmilk_freq                                    -6.031e-17  1.406e-16
as.factor(sweetPref)High:as.factor(fatPref)Medium -3.953e-15  1.357e-15
as.factor(sweetPref)High:as.factor(fatPref)High   -3.867e-15  1.516e-15
                                                     t value Pr(>|t|)    
(Intercept)                                        2.743e+15  < 2e-16 ***
as.factor(sweetPref)High                           3.611e+00  0.00040 ***
as.factor(fatPref)Medium                           3.337e+00  0.00104 ** 
as.factor(fatPref)High                             2.859e+00  0.00478 ** 
age                                               -7.670e-01  0.44399    
plantmilk_freq                                    -4.290e-01  0.66844    
as.factor(sweetPref)High:as.factor(fatPref)Medium -2.913e+00  0.00405 ** 
as.factor(sweetPref)High:as.factor(fatPref)High   -2.551e+00  0.01162 *  
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 3.094e-15 on 172 degrees of freedom
Multiple R-squared:  0.4922,    Adjusted R-squared:  0.4715 
F-statistic: 23.82 on 7 and 172 DF,  p-value: < 2.2e-16
Code
summary.aov(tproteinHEI.lm)
                                         Df    Sum Sq   Mean Sq F value  Pr(>F)
as.factor(sweetPref)                      1 3.540e-29 3.540e-29   3.698 0.05612
as.factor(fatPref)                        2 2.850e-29 1.423e-29   1.486 0.22914
age                                       1 6.400e-30 6.430e-30   0.672 0.41359
plantmilk_freq                            1 6.000e-31 5.600e-31   0.058 0.80997
as.factor(sweetPref):as.factor(fatPref)   2 9.320e-29 4.661e-29   4.869 0.00877
Residuals                               172 1.646e-27 9.570e-30                
                                          
as.factor(sweetPref)                    . 
as.factor(fatPref)                        
age                                       
plantmilk_freq                            
as.factor(sweetPref):as.factor(fatPref) **
Residuals                                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
emmeans(tproteinHEI.lm, ~sweetPref)
Warning in summary.lm(object, ...): essentially perfect fit: summary may be
unreliable
NOTE: Results may be misleading due to involvement in interactions
 sweetPref emmean       SE  df lower.CL upper.CL
 Low         4.97 5.19e-16 172     4.97     4.97
 High        4.97 2.68e-16 172     4.97     4.97

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 
Code
emmeans(tproteinHEI.lm, ~fatPref)
Warning in summary.lm(object, ...): essentially perfect fit: summary may be
unreliable
NOTE: Results may be misleading due to involvement in interactions
 fatPref emmean       SE  df lower.CL upper.CL
 Low       4.97 5.35e-16 172     4.97     4.97
 Medium    4.97 4.16e-16 172     4.97     4.97
 High      4.97 5.53e-16 172     4.97     4.97

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 
Code
## SF protein HEI
sfpproteinHEI.lm <- full.df %>%
  lm(sfpproteinHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(sfpproteinHEI.lm)

Call:
lm(formula = sfpproteinHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
    Min      1Q  Median      3Q     Max 
-0.5086 -0.4174 -0.2715 -0.1995  2.4997 

Coefficients:
                                                   Estimate Std. Error t value
(Intercept)                                        1.549332   0.513584   3.017
as.factor(sweetPref)High                           0.393827   0.303851   1.296
as.factor(fatPref)Medium                           0.281661   0.332469   0.847
as.factor(fatPref)High                             0.243323   0.389397   0.625
age                                               -0.004369   0.020751  -0.211
plantmilk_freq                                     0.014234   0.039844   0.357
as.factor(sweetPref)High:as.factor(fatPref)Medium -0.455711   0.384661  -1.185
as.factor(sweetPref)High:as.factor(fatPref)High   -0.190152   0.429736  -0.442
                                                  Pr(>|t|)   
(Intercept)                                        0.00294 **
as.factor(sweetPref)High                           0.19667   
as.factor(fatPref)Medium                           0.39807   
as.factor(fatPref)High                             0.53288   
age                                                0.83351   
plantmilk_freq                                     0.72135   
as.factor(sweetPref)High:as.factor(fatPref)Medium  0.23777   
as.factor(sweetPref)High:as.factor(fatPref)High    0.65869   
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 0.877 on 172 degrees of freedom
Multiple R-squared:  0.02181,   Adjusted R-squared:  -0.018 
F-statistic: 0.5478 on 7 and 172 DF,  p-value: 0.7972
Code
summary.aov(sfpproteinHEI.lm)
                                         Df Sum Sq Mean Sq F value Pr(>F)
as.factor(sweetPref)                      1   0.65  0.6509   0.846  0.359
as.factor(fatPref)                        2   1.05  0.5239   0.681  0.507
age                                       1   0.00  0.0048   0.006  0.937
plantmilk_freq                            1   0.11  0.1136   0.148  0.701
as.factor(sweetPref):as.factor(fatPref)   2   1.13  0.5659   0.736  0.481
Residuals                               172 132.28  0.7691               
Code
## Fat HEI
fatHEI.lm <- full.df %>%
  lm(fatHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(fatHEI.lm)

Call:
lm(formula = fatHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
    Min      1Q  Median      3Q     Max 
-1.5845 -0.8184 -0.6253  0.9508  3.0617 

Coefficients:
                                                  Estimate Std. Error t value
(Intercept)                                        3.86282    0.77422   4.989
as.factor(sweetPref)High                           0.04679    0.45805   0.102
as.factor(fatPref)Medium                           0.67500    0.50119   1.347
as.factor(fatPref)High                             0.41726    0.58701   0.711
age                                               -0.04321    0.03128  -1.381
plantmilk_freq                                     0.08568    0.06006   1.427
as.factor(sweetPref)High:as.factor(fatPref)Medium -0.51716    0.57987  -0.892
as.factor(sweetPref)High:as.factor(fatPref)High   -0.27149    0.64782  -0.419
                                                  Pr(>|t|)    
(Intercept)                                       1.47e-06 ***
as.factor(sweetPref)High                             0.919    
as.factor(fatPref)Medium                             0.180    
as.factor(fatPref)High                               0.478    
age                                                  0.169    
plantmilk_freq                                       0.156    
as.factor(sweetPref)High:as.factor(fatPref)Medium    0.374    
as.factor(sweetPref)High:as.factor(fatPref)High      0.676    
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 1.322 on 172 degrees of freedom
Multiple R-squared:  0.04436,   Adjusted R-squared:  0.005466 
F-statistic: 1.141 on 7 and 172 DF,  p-value: 0.34
Code
## Grain HEI
grainHEI.lm <- full.df %>%
  lm(grainHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(grainHEI.lm)

Call:
lm(formula = grainHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
   Min     1Q Median     3Q    Max 
-2.927 -1.763 -1.230  1.024  6.020 

Coefficients:
                                                  Estimate Std. Error t value
(Intercept)                                        3.65615    1.47694   2.475
as.factor(sweetPref)High                          -1.27628    0.87380  -1.461
as.factor(fatPref)Medium                          -0.39855    0.95610  -0.417
as.factor(fatPref)High                            -0.87749    1.11981  -0.784
age                                                0.06800    0.05967   1.140
plantmilk_freq                                    -0.09376    0.11458  -0.818
as.factor(sweetPref)High:as.factor(fatPref)Medium  0.33129    1.10619   0.299
as.factor(sweetPref)High:as.factor(fatPref)High    1.60533    1.23581   1.299
                                                  Pr(>|t|)  
(Intercept)                                         0.0143 *
as.factor(sweetPref)High                            0.1459  
as.factor(fatPref)Medium                            0.6773  
as.factor(fatPref)High                              0.4343  
age                                                 0.2561  
plantmilk_freq                                      0.4143  
as.factor(sweetPref)High:as.factor(fatPref)Medium   0.7649  
as.factor(sweetPref)High:as.factor(fatPref)High     0.1957  
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 2.522 on 172 degrees of freedom
Multiple R-squared:  0.03765,   Adjusted R-squared:  -0.001515 
F-statistic: 0.9613 on 7 and 172 DF,  p-value: 0.4612
Code
## Sodium HEI
sodiumHEI.lm <- full.df %>%
  lm(sodiumHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(sodiumHEI.lm)

Call:
lm(formula = sodiumHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
    Min      1Q  Median      3Q     Max 
-3.3864 -1.8923  0.1599  1.5706  3.7447 

Coefficients:
                                                  Estimate Std. Error t value
(Intercept)                                        6.17360    1.17436   5.257
as.factor(sweetPref)High                          -1.29526    0.69478  -1.864
as.factor(fatPref)Medium                          -0.19099    0.76022  -0.251
as.factor(fatPref)High                            -0.94951    0.89039  -1.066
age                                               -0.04854    0.04745  -1.023
plantmilk_freq                                    -0.16364    0.09111  -1.796
as.factor(sweetPref)High:as.factor(fatPref)Medium -0.20956    0.87956  -0.238
as.factor(sweetPref)High:as.factor(fatPref)High    1.19487    0.98263   1.216
                                                  Pr(>|t|)    
(Intercept)                                        4.3e-07 ***
as.factor(sweetPref)High                            0.0640 .  
as.factor(fatPref)Medium                            0.8019    
as.factor(fatPref)High                              0.2877    
age                                                 0.3078    
plantmilk_freq                                      0.0742 .  
as.factor(sweetPref)High:as.factor(fatPref)Medium   0.8120    
as.factor(sweetPref)High:as.factor(fatPref)High     0.2257    
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 2.005 on 172 degrees of freedom
Multiple R-squared:  0.07958,   Adjusted R-squared:  0.04212 
F-statistic: 2.125 on 7 and 172 DF,  p-value: 0.04345
Code
summary.aov(sodiumHEI.lm)
                                         Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1   25.9  25.905   6.442 0.0120 *
as.factor(fatPref)                        2    2.9   1.437   0.357 0.7000  
age                                       1    5.5   5.544   1.379 0.2420  
plantmilk_freq                            1   14.7  14.653   3.644 0.0579 .
as.factor(sweetPref):as.factor(fatPref)   2   10.8   5.412   1.346 0.2630  
Residuals                               172  691.6   4.021                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
emmeans(sodiumHEI.lm, pairwise ~ sweetPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         4.25 0.336 172     3.59     4.91
 High        3.28 0.174 172     2.94     3.62

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 

$contrasts
 contrast   estimate    SE  df t.ratio p.value
 Low - High    0.967 0.382 172   2.533  0.0122

Results are averaged over the levels of: fatPref 
Code
emmeans(sodiumHEI.lm, ~ sweetPref)
NOTE: Results may be misleading due to involvement in interactions
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         4.25 0.336 172     3.59     4.91
 High        3.28 0.174 172     2.94     3.62

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 
Code
## Sugar HEI
sugarHEI.lm <- full.df %>%
  lm(sugarHEI ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(sugarHEI.lm)

Call:
lm(formula = sugarHEI ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
    Min      1Q  Median      3Q     Max 
-5.9762 -2.7628  0.8739  1.3687  6.8578 

Coefficients:
                                                  Estimate Std. Error t value
(Intercept)                                        4.43300    1.54543   2.868
as.factor(sweetPref)High                          -2.33088    0.91432  -2.549
as.factor(fatPref)Medium                          -1.14401    1.00044  -1.144
as.factor(fatPref)High                            -0.47141    1.17174  -0.402
age                                                0.10063    0.06244   1.612
plantmilk_freq                                    -0.21799    0.11990  -1.818
as.factor(sweetPref)High:as.factor(fatPref)Medium  1.17490    1.15749   1.015
as.factor(sweetPref)High:as.factor(fatPref)High    0.62515    1.29312   0.483
                                                  Pr(>|t|)   
(Intercept)                                        0.00464 **
as.factor(sweetPref)High                           0.01167 * 
as.factor(fatPref)Medium                           0.25441   
as.factor(fatPref)High                             0.68795   
age                                                0.10888   
plantmilk_freq                                     0.07077 . 
as.factor(sweetPref)High:as.factor(fatPref)Medium  0.31151   
as.factor(sweetPref)High:as.factor(fatPref)High    0.62940   
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 2.639 on 172 degrees of freedom
Multiple R-squared:  0.08207,   Adjusted R-squared:  0.04471 
F-statistic: 2.197 on 7 and 172 DF,  p-value: 0.03676
Code
summary.aov(sugarHEI.lm)
                                         Df Sum Sq Mean Sq F value  Pr(>F)   
as.factor(sweetPref)                      1   61.9   61.91   8.891 0.00328 **
as.factor(fatPref)                        2    2.3    1.17   0.167 0.84606   
age                                       1   11.6   11.63   1.671 0.19789   
plantmilk_freq                            1   24.0   23.97   3.442 0.06526 . 
as.factor(sweetPref):as.factor(fatPref)   2    7.2    3.62   0.520 0.59547   
Residuals                               172 1197.8    6.96                   
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
emmeans(sugarHEI.lm, pairwise ~ sweetPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         5.39 0.442 172     4.52     6.27
 High        3.66 0.229 172     3.21     4.11

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 

$contrasts
 contrast   estimate    SE  df t.ratio p.value
 Low - High     1.73 0.502 172   3.446  0.0007

Results are averaged over the levels of: fatPref 
Code
emmeans(sugarHEI.lm, ~sweetPref)
NOTE: Results may be misleading due to involvement in interactions
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         5.39 0.442 172     4.52     6.27
 High        3.66 0.229 172     3.21     4.11

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 
Code
## Sugar intake
sugarintake.lm <- full.df %>%
  lm(sugar.intake ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(sugarintake.lm)

Call:
lm(formula = sugar.intake ~ as.factor(sweetPref) * as.factor(fatPref) + 
    age + plantmilk_freq, data = .)

Residuals:
    Min      1Q  Median      3Q     Max 
-411.43 -213.78  -53.77  111.29  974.25 

Coefficients:
                                                  Estimate Std. Error t value
(Intercept)                                        330.738    154.328   2.143
as.factor(sweetPref)High                           152.691     91.305   1.672
as.factor(fatPref)Medium                           105.861     99.905   1.060
as.factor(fatPref)High                              60.868    117.011   0.520
age                                                 -1.299      6.236  -0.208
plantmilk_freq                                      13.622     11.973   1.138
as.factor(sweetPref)High:as.factor(fatPref)Medium  -88.691    115.588  -0.767
as.factor(sweetPref)High:as.factor(fatPref)High    -71.443    129.132  -0.553
                                                  Pr(>|t|)  
(Intercept)                                         0.0335 *
as.factor(sweetPref)High                            0.0963 .
as.factor(fatPref)Medium                            0.2908  
as.factor(fatPref)High                              0.6036  
age                                                 0.8352  
plantmilk_freq                                      0.2568  
as.factor(sweetPref)High:as.factor(fatPref)Medium   0.4440  
as.factor(sweetPref)High:as.factor(fatPref)High     0.5808  
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 263.5 on 172 degrees of freedom
Multiple R-squared:  0.03057,   Adjusted R-squared:  -0.008887 
F-statistic: 0.7747 on 7 and 172 DF,  p-value: 0.6093
Code
summary.aov(sugarintake.lm)
                                         Df   Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1   194270  194270   2.797 0.0962 .
as.factor(fatPref)                        2    42961   21480   0.309 0.7344  
age                                       1        3       3   0.000 0.9945  
plantmilk_freq                            1    96892   96892   1.395 0.2392  
as.factor(sweetPref):as.factor(fatPref)   2    42487   21243   0.306 0.7369  
Residuals                               172 11944385   69444                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Group difference, pref.cal, anthropometrics

Code
## BMI
BMI.aov <- full.df %>%
  aov(BMI ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(BMI.aov)
                        Df Sum Sq Mean Sq F value   Pr(>F)    
as.factor(prefcal.cat)   2     23    11.4   0.283    0.754    
age                      1    841   840.8  20.804 9.54e-06 ***
plantmilk_freq           1     10     9.9   0.246    0.620    
Residuals              175   7073    40.4                     
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
## WC
WC.aov <- full.df %>%
  aov(WC ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(WC.aov)
                        Df Sum Sq Mean Sq F value   Pr(>F)    
as.factor(prefcal.cat)   2      4     2.2   0.081    0.923    
age                      1    536   535.5  19.607 1.67e-05 ***
plantmilk_freq           1      2     2.0   0.072    0.788    
Residuals              175   4780    27.3                     
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
## Lean mass
leanmass.aov <- full.df %>%
  aov(lean_mass ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(leanmass.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2     61   30.29   1.357 0.2606  
age                      1     83   82.65   3.704 0.0562 .
plantmilk_freq           1      0    0.03   0.001 0.9714  
Residuals              145   3235   22.31                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## SMM
SMM.aov <- full.df %>%
  aov(SMM ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(SMM.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2    266   133.0   1.173 0.3123  
age                      1    417   416.6   3.675 0.0572 .
plantmilk_freq           1      0     0.1   0.001 0.9758  
Residuals              145  16437   113.4                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## SMM, weight adjusted
SMMwt.aov <- full.df %>%
    aov(SMM_wt ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(SMMwt.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2   51.1   25.56   1.597 0.2061  
age                      1   35.4   35.38   2.210 0.1393  
plantmilk_freq           1   51.2   51.19   3.199 0.0758 .
Residuals              145 2320.7   16.00                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## FFM
FFM.aov <- full.df %>%
    aov(FFM ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(FFM.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2    741   370.3   1.186 0.3085  
age                      1   1139  1138.8   3.646 0.0582 .
plantmilk_freq           1      0     0.1   0.000 0.9857  
Residuals              145  45294   312.4                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## Trunk lean mass
trunklean.aov <- full.df %>%
    aov(trunk_lean_mass ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(trunklean.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2     95   47.56   0.716  0.490  
age                      1    304  304.27   4.580  0.034 *
plantmilk_freq           1      4    3.63   0.055  0.816  
Residuals              145   9633   66.43                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## Trunk fat mass
trunkfat.aov <- full.df %>%
    aov(trunk_fat_mass ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(trunkfat.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2     28    14.2   0.096 0.9088  
age                      1    840   839.8   5.674 0.0185 *
plantmilk_freq           1    293   292.5   1.977 0.1619  
Residuals              145  21459   148.0                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## Visceral fat mass
visceralfat.aov <- full.df %>%
    aov(visceral_fat ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(visceralfat.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2    881     441   0.149 0.8615  
age                      1  16878   16878   5.715 0.0181 *
plantmilk_freq           1   8517    8517   2.884 0.0916 .
Residuals              145 428235    2953                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## BFM
BFMfat.aov <- full.df %>%
    aov(BFM ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(BFMfat.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2    104    52.0   0.079 0.9238  
age                      1   2816  2816.5   4.291 0.0401 *
plantmilk_freq           1   1639  1638.5   2.496 0.1163  
Residuals              145  95168   656.3                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## PBF
PBFfat.aov <- full.df %>%
      aov(PBF ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(BFMfat.aov)
                        Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2    104    52.0   0.079 0.9238  
age                      1   2816  2816.5   4.291 0.0401 *
plantmilk_freq           1   1639  1638.5   2.496 0.1163  
Residuals              145  95168   656.3                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## BMR
BMRfat.aov <- full.df %>%
      aov(BMR ~ as.factor(prefcal.cat) + age + plantmilk_freq, .)
summary(BMRfat.aov)
                        Df  Sum Sq Mean Sq F value Pr(>F)  
as.factor(prefcal.cat)   2   71339   35669   1.189 0.3076  
age                      1  109962  109962   3.665 0.0575 .
plantmilk_freq           1       7       7   0.000 0.9878  
Residuals              145 4350905   30006                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness

Group difference, 2x2 ANOVA, anthropometrics

Code
## BMI
BMI.aov <- full.df %>%
  aov(BMI ~ sweetPref*fatPref + age + plantmilk_freq, .)
summary(BMI.aov)
                   Df Sum Sq Mean Sq F value   Pr(>F)    
sweetPref           1    133   133.3   3.393   0.0672 .  
fatPref             2    172    85.8   2.184   0.1158    
age                 1    801   801.5  20.398 1.16e-05 ***
plantmilk_freq      1      0     0.1   0.003   0.9561    
sweetPref:fatPref   2     82    41.0   1.042   0.3549    
Residuals         172   6758    39.3                     
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
emmeans(BMI.aov, pairwise ~ sweetPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         23.5 1.050 172     21.4     25.5
 High        25.7 0.543 172     24.7     26.8

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 

$contrasts
 contrast   estimate   SE  df t.ratio p.value
 Low - High    -2.28 1.19 172  -1.913  0.0574

Results are averaged over the levels of: fatPref 
Code
emmeans(BMI.aov, ~sweetPref)
NOTE: Results may be misleading due to involvement in interactions
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         23.5 1.050 172     21.4     25.5
 High        25.7 0.543 172     24.7     26.8

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 
Code
## WC
WC.aov <- full.df %>%
  aov(WC ~ sweetPref*fatPref + age + plantmilk_freq, .)
summary(WC.aov)
                   Df Sum Sq Mean Sq F value   Pr(>F)    
sweetPref           1     49    48.8   1.830    0.178    
fatPref             2     84    42.1   1.575    0.210    
age                 1    518   517.7  19.394 1.86e-05 ***
plantmilk_freq      1      0     0.4   0.015    0.902    
sweetPref:fatPref   2     80    39.9   1.494    0.227    
Residuals         172   4591    26.7                     
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Code
## Lean mass
leanmass.aov <- full.df %>%
  aov(lean_mass ~ as.factor(sweetPref) * as.factor(fatPref) + age + plantmilk_freq, .)
summary(leanmass.aov)
                                         Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1   12.4   12.42   0.565 0.4533  
as.factor(fatPref)                        2   83.9   41.95   1.910 0.1519  
age                                       1   75.3   75.33   3.430 0.0661 .
plantmilk_freq                            1    1.5    1.46   0.067 0.7966  
as.factor(sweetPref):as.factor(fatPref)   2   86.8   43.39   1.975 0.1425  
Residuals                               142 3118.7   21.96                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## SMM
SMM.aov <- full.df %>%
  aov(SMM ~ as.factor(sweetPref) * as.factor(fatPref) + age + plantmilk_freq, .)
summary(SMM.aov)
                                         Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1     59    59.0   0.533 0.4667  
as.factor(fatPref)                        2    488   244.0   2.204 0.1141  
age                                       1    384   383.7   3.466 0.0647 .
plantmilk_freq                            1      8     8.1   0.073 0.7869  
as.factor(sweetPref):as.factor(fatPref)   2    461   230.5   2.082 0.1284  
Residuals                               142  15720   110.7                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## SMM, weight adjusted
SMMwt.aov <- full.df %>%
    aov(SMM_wt ~ sweetPref * fatPref + age + plantmilk_freq, .)
summary(SMMwt.aov)
                   Df Sum Sq Mean Sq F value Pr(>F)  
sweetPref           1   55.5   55.54   3.465 0.0647 .
fatPref             2   63.0   31.51   1.966 0.1438  
age                 1   42.3   42.30   2.639 0.1065  
plantmilk_freq      1   17.3   17.29   1.079 0.3008  
sweetPref:fatPref   2    4.4    2.19   0.137 0.8725  
Residuals         142 2275.9   16.03                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
emmeans(SMMwt.aov, pairwise ~ sweetPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         36.8 0.788 142     35.3     38.4
 High        35.5 0.379 142     34.7     36.2

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 

$contrasts
 contrast   estimate    SE  df t.ratio p.value
 Low - High     1.33 0.881 142   1.516  0.1318

Results are averaged over the levels of: fatPref 
Code
emmeans(SMMwt.aov, ~sweetPref)
NOTE: Results may be misleading due to involvement in interactions
 sweetPref emmean    SE  df lower.CL upper.CL
 Low         36.8 0.788 142     35.3     38.4
 High        35.5 0.379 142     34.7     36.2

Results are averaged over the levels of: fatPref 
Confidence level used: 0.95 
Code
## FFM
FFM.aov <- full.df %>%
    aov(FFM ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(FFM.aov)
                                         Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1    189   189.2   0.619 0.4327  
as.factor(fatPref)                        2   1291   645.7   2.112 0.1247  
age                                       1   1045  1044.6   3.417 0.0666 .
plantmilk_freq                            1     13    13.3   0.043 0.8352  
as.factor(sweetPref):as.factor(fatPref)   2   1226   613.0   2.005 0.1384  
Residuals                               142  43409   305.7                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## Trunk lean mass
trunklean.aov <- full.df %>%
    aov(trunk_lean_mass ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(trunklean.aov)
                                         Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1     56   55.69   0.874 0.3515  
as.factor(fatPref)                        2    324  161.89   2.540 0.0825 .
age                                       1    287  287.02   4.503 0.0356 *
plantmilk_freq                            1      0    0.19   0.003 0.9562  
as.factor(sweetPref):as.factor(fatPref)   2    318  158.85   2.492 0.0864 .
Residuals                               142   9052   63.74                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
## Trunk fat mass
trunkfat.aov <- full.df %>%
    aov(trunk_fat_mass ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(trunkfat.aov)
                                         Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1    374   373.9   2.649 0.1058  
as.factor(fatPref)                        2    965   482.5   3.419 0.0355 *
age                                       1    868   868.1   6.151 0.0143 *
plantmilk_freq                            1     85    84.9   0.601 0.4393  
as.factor(sweetPref):as.factor(fatPref)   2    287   143.5   1.017 0.3644  
Residuals                               142  20041   141.1                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
emmeans(trunkfat.aov, pairwise ~ fatPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 fatPref emmean   SE  df lower.CL upper.CL
 Low       26.6 2.68 142     21.3     31.9
 Medium    22.7 1.74 142     19.3     26.1
 High      21.0 2.26 142     16.5     25.4

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 

$contrasts
 contrast      estimate   SE  df t.ratio p.value
 Low - Medium      3.87 3.19 142   1.215  0.4465
 Low - High        5.60 3.55 142   1.581  0.2573
 Medium - High     1.73 2.87 142   0.602  0.8192

Results are averaged over the levels of: sweetPref 
P value adjustment: tukey method for comparing a family of 3 estimates 
Code
emmeans(trunkfat.aov, ~ fatPref)
NOTE: Results may be misleading due to involvement in interactions
 fatPref emmean   SE  df lower.CL upper.CL
 Low       26.6 2.68 142     21.3     31.9
 Medium    22.7 1.74 142     19.3     26.1
 High      21.0 2.26 142     16.5     25.4

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 
Code
## Visceral fat mass
visceralfat.aov <- full.df %>%
    aov(visceral_fat ~ as.factor(sweetPref)*as.factor(fatPref) + age + plantmilk_freq, .)
summary(visceralfat.aov)
                                         Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)                      1   8347    8347   2.937 0.0887 .
as.factor(fatPref)                        2  17440    8720   3.069 0.0496 *
age                                       1  17505   17505   6.160 0.0142 *
plantmilk_freq                            1   3233    3233   1.138 0.2879  
as.factor(sweetPref):as.factor(fatPref)   2   4475    2237   0.787 0.4570  
Residuals                               142 403510    2842                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
emmeans(visceralfat.aov, pairwise ~ fatPref, adjust = "tukey")
NOTE: Results may be misleading due to involvement in interactions
$emmeans
 fatPref emmean    SE  df lower.CL upper.CL
 Low      112.9 12.00 142     89.1      137
 Medium    96.2  7.79 142     80.8      112
 High      89.3 10.10 142     69.3      109

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 

$contrasts
 contrast      estimate   SE  df t.ratio p.value
 Low - Medium      16.7 14.3 142   1.165  0.4760
 Low - High        23.6 15.9 142   1.481  0.3029
 Medium - High      6.9 12.9 142   0.535  0.8543

Results are averaged over the levels of: sweetPref 
P value adjustment: tukey method for comparing a family of 3 estimates 
Code
emmeans(visceralfat.aov, ~ fatPref)
NOTE: Results may be misleading due to involvement in interactions
 fatPref emmean    SE  df lower.CL upper.CL
 Low      112.9 12.00 142     89.1      137
 Medium    96.2  7.79 142     80.8      112
 High      89.3 10.10 142     69.3      109

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 
Code
## BFM
BFMfat.aov <- full.df %>%
    aov(BFM ~ as.factor(sweetPref) + as.factor(fatPref) + age + plantmilk_freq, .)
summary(BFMfat.aov)
                      Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)   1   1695  1694.7   2.726 0.1009  
as.factor(fatPref)     2   5052  2526.0   4.063 0.0192 *
age                    1   2934  2934.2   4.719 0.0315 *
plantmilk_freq         1    511   510.9   0.822 0.3662  
Residuals            144  89535   621.8                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
emmeans(BFMfat.aov, pairwise ~ fatPref, adjust = "tukey")
$emmeans
 fatPref emmean   SE  df lower.CL upper.CL
 Low       58.5 4.59 144     49.4     67.6
 Medium    45.1 3.43 144     38.4     51.9
 High      45.2 3.91 144     37.5     52.9

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 

$contrasts
 contrast      estimate   SE  df t.ratio p.value
 Low - Medium   13.3326 5.38 144   2.480  0.0378
 Low - High     13.2663 5.61 144   2.365  0.0505
 Medium - High  -0.0662 4.83 144  -0.014  0.9999

Results are averaged over the levels of: sweetPref 
P value adjustment: tukey method for comparing a family of 3 estimates 
Code
emmeans(BFMfat.aov, ~ fatPref)
 fatPref emmean   SE  df lower.CL upper.CL
 Low       58.5 4.59 144     49.4     67.6
 Medium    45.1 3.43 144     38.4     51.9
 High      45.2 3.91 144     37.5     52.9

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 
Code
## PBF
PBFfat.aov <- full.df %>%
      aov(PBF ~ as.factor(sweetPref) + as.factor(fatPref) + age + plantmilk_freq, .)
summary(BFMfat.aov)
                      Df Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)   1   1695  1694.7   2.726 0.1009  
as.factor(fatPref)     2   5052  2526.0   4.063 0.0192 *
age                    1   2934  2934.2   4.719 0.0315 *
plantmilk_freq         1    511   510.9   0.822 0.3662  
Residuals            144  89535   621.8                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness
Code
emmeans(PBFfat.aov, pairwise ~ fatPref, adjust = "tukey")
$emmeans
 fatPref emmean   SE  df lower.CL upper.CL
 Low       35.4 1.37 144     32.7     38.1
 Medium    32.7 1.03 144     30.6     34.7
 High      32.2 1.17 144     29.8     34.5

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 

$contrasts
 contrast      estimate   SE  df t.ratio p.value
 Low - Medium     2.755 1.61 144   1.713  0.2038
 Low - High       3.246 1.68 144   1.935  0.1327
 Medium - High    0.492 1.44 144   0.341  0.9380

Results are averaged over the levels of: sweetPref 
P value adjustment: tukey method for comparing a family of 3 estimates 
Code
emmeans(PBFfat.aov, ~ fatPref)
 fatPref emmean   SE  df lower.CL upper.CL
 Low       35.4 1.37 144     32.7     38.1
 Medium    32.7 1.03 144     30.6     34.7
 High      32.2 1.17 144     29.8     34.5

Results are averaged over the levels of: sweetPref 
Confidence level used: 0.95 
Code
## BMR
BMRfat.aov <- full.df %>%
      aov(BMR ~ as.factor(sweetPref) + as.factor(fatPref) + age + plantmilk_freq, .)
summary(BMRfat.aov)
                      Df  Sum Sq Mean Sq F value Pr(>F)  
as.factor(sweetPref)   1   18157   18157   0.610 0.4362  
as.factor(fatPref)     2  124126   62063   2.084 0.1281  
age                    1  100880  100880   3.388 0.0677 .
plantmilk_freq         1    1314    1314   0.044 0.8339  
Residuals            144 4287735   29776                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
30 observations deleted due to missingness

Response Surface Methodology

Code
rsm.df <- oatmilk.liking.long %>%
  separate(sample, into = c("sugar.level", "fat.level"), sep = 2) %>%
  group_by(sugar.level, fat.level) %>%
  summarize(liking = mean(liking), .groups = "drop") %>%
  mutate(sugar.percent = case_when(
    sugar.level == "S0" ~ 0,
    sugar.level == "S1" ~ 14,
    sugar.level == "S2" ~ 28
  )) %>%
  mutate(fat.percent = case_when(
    fat.level == "F0" ~ 0,
    fat.level == "F1" ~ 2,
    fat.level == "F2" ~ 6,
    fat.level == "F3" ~ 12
    )) %>%
  select(c(sugar.percent, fat.percent, liking))

## Base RSM model
rsm.model <- rsm(liking ~ SO(sugar.percent, fat.percent), data = rsm.df)
summary(rsm.model)

Call:
rsm(formula = liking ~ SO(sugar.percent, fat.percent), data = rsm.df)

                           Estimate Std. Error t value Pr(>|t|)   
(Intercept)               43.741667   6.151668  7.1105 0.005724 **
sugar.percent             -1.015591   0.970005 -1.0470 0.372023   
fat.percent                1.249251   2.325479  0.5372 0.628416   
sugar.percent:fat.percent  0.069997   0.067802  1.0324 0.377828   
sugar.percent^2            0.038573   0.030870  1.2495 0.300080   
fat.percent^2             -0.162574   0.144584 -1.1244 0.342681   
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Multiple R-squared:  0.8276,    Adjusted R-squared:  0.5402 
F-statistic:  2.88 on 5 and 3 DF,  p-value: 0.2065

Analysis of Variance Table

Response: liking
                                Df Sum Sq Mean Sq F value Pr(>F)
FO(sugar.percent, fat.percent)   2 290.65 145.323  3.8402 0.1489
TWI(sugar.percent, fat.percent)  1 163.90 163.897  4.3310 0.1289
PQ(sugar.percent, fat.percent)   2  90.40  45.200  1.1944 0.4154
Residuals                        3 113.53  37.843               
Lack of fit                      3 113.53  37.843     NaN    NaN
Pure error                       0   0.00     NaN               

Stationary point of response surface:
sugar.percent   fat.percent 
     8.096881      5.585192 

Eigenanalysis:
eigen() decomposition
$values
[1]  0.04448869 -0.16848927

$vectors
                    [,1]       [,2]
sugar.percent -0.9860143 -0.1666605
fat.percent   -0.1666605  0.9860143
Code
persp(rsm.model, ~ sugar.percent + fat.percent, col = c("lightblue", "lightyellow", "pink"))

Code
## Central Composite Design model 
oatmilk.coded <- coded.data(rsm.df, x1 ~(Sugar-110)/110, x2 ~(Acid-10)/10) ## Center variables around 0