Untitled

Shiny Documents

This Quarto document is made interactive using Shiny. Interactive documents allow readers to modify parameters and see the results immediately. Learn more about Shiny interactive documents at https://quarto.org/docs/interactive/shiny/.

Inputs and Outputs

You can embed Shiny inputs and outputs in your document. Outputs are automatically updated whenever inputs change. This demonstrates how a standard R plot can be made interactive:

# Package names, add everything you want to load OR install 
packages <- c("dplyr","tidyr", "knitr", "plotly", "readxl", "tidyverse", "text2vec", "caret", "e1071", "glmnet", "ggplot2", "sf", "rnaturalearth", "rnaturalearth", "gganimate", "concaveman", "leaflet", "shiny")

# Install packages not yet installed
installed_packages <- packages %in% rownames(installed.packages())
if (any(installed_packages == FALSE)) {
  install.packages(packages[!installed_packages])
}

# Packages loading
invisible(lapply(packages, library, character.only = TRUE))

Attaching package: 'dplyr'
The following objects are masked from 'package:stats':

    filter, lag
The following objects are masked from 'package:base':

    intersect, setdiff, setequal, union
Loading required package: ggplot2

Attaching package: 'plotly'
The following object is masked from 'package:ggplot2':

    last_plot
The following object is masked from 'package:stats':

    filter
The following object is masked from 'package:graphics':

    layout
── Attaching core tidyverse packages ──────────────────────── tidyverse 2.0.0 ──
✔ forcats   1.0.0     ✔ readr     2.1.4
✔ lubridate 1.9.2     ✔ stringr   1.5.1
✔ purrr     1.0.2     ✔ tibble    3.2.1
── Conflicts ────────────────────────────────────────── tidyverse_conflicts() ──
✖ plotly::filter() masks dplyr::filter(), stats::filter()
✖ dplyr::lag()     masks stats::lag()
ℹ Use the conflicted package (<http://conflicted.r-lib.org/>) to force all conflicts to become errors
Warning: package 'text2vec' was built under R version 4.3.3
Warning: package 'caret' was built under R version 4.3.3
Loading required package: lattice

Attaching package: 'caret'

The following object is masked from 'package:purrr':

    lift
Warning: package 'e1071' was built under R version 4.3.3
Loading required package: Matrix

Attaching package: 'Matrix'

The following objects are masked from 'package:tidyr':

    expand, pack, unpack

Loaded glmnet 4.1-7
Warning: package 'sf' was built under R version 4.3.3
Linking to GEOS 3.11.0, GDAL 3.5.3, PROJ 9.1.0; sf_use_s2() is TRUE
d= read.csv("../data/conflict_data/Israel_Palestine_Jan17.csv")
# Convert to an sf object (simple features)
locations_sf <- st_as_sf(d, coords = c("longitude", "latitude"), crs = 4326)


# Generate the concave hull
concave_hull <- concaveman(locations_sf, concavity = 2)

israel_sf <- ne_countries(scale = "medium", country = "Israel", returnclass = "sf")

# UI
ui <- fluidPage(
  titlePanel("Conflict Events Map with Concave Hull Measuring Area of Conflict Disperion"),
  
  sidebarLayout(
    sidebarPanel(
      # Date selector for conflict events
      dateInput("date", 
                "Select Date:", 
                value =  "2025-01-07",
                min = min(locations_sf$event_date), 
                max = max(locations_sf$event_date),
                format = "yyyy-mm-dd"),
      
      # Slider input for concavity
      sliderInput("concavity", 
                  "Select Concavity:", 
                  min = 1, 
                  max = 5, 
                  value = 2, 
                  step = 0.1)
    ),
    
    mainPanel(
      leafletOutput("map"), # Output the map
       # Output the computed area
      textOutput("concave_area")
    )
  )
)

# Server
server <- function(input, output, session) {
  
  output$map <- renderLeaflet({
    
    # Filter the locations based on the selected date
    selected_data <- locations_sf[locations_sf$event_date == input$date, ]
    
    # Calculate the concave hull based on the selected concavity
    concave_hull <- concaveman(selected_data, concavity = input$concavity)
    
    
    # Calculate the area of the concave hull
    concave_area <- st_area(concave_hull)
    
    # Convert area from units of meters squared (default) to km² or any other unit if needed
    concave_area_km2 <- concave_area / 1e6 
    
     # Store the computed area to display on the UI
    output$concave_area <- renderText({
      paste("Area of diffusion of conflict: ", round(concave_area_km2, 2), "km²")
    })
    
    
    # Generate the leaflet map with the updated concave hull
    leaflet() %>%
      addTiles() %>%  # Add a basemap
      addPolygons(data = israel_sf, color = "black", fillColor = "lightgray", weight = 1) %>%  # Israel map
      addPolygons(data = concave_hull, color = "blue", fillOpacity = 0.3) %>%  # Concave hull
      addCircleMarkers(data = selected_data, color = "red", radius = 4, label = ~location)  # Conflict points
  })
}


# Run the application
shinyApp(ui = ui, server = server)