diff --git a/code/game/objects/structures/flora.dm b/code/game/objects/structures/flora.dm
index e08dba0a0f..5976c35703 100644
--- a/code/game/objects/structures/flora.dm
+++ b/code/game/objects/structures/flora.dm
@@ -1,78 +1,6 @@
-//trees
-/obj/structure/flora/tree
- name = "tree"
- anchored = 1
- density = 1
- pixel_x = -16
- layer = MOB_LAYER // You know what, let's play it safe.
-
-/obj/structure/flora/tree/pine
- name = "pine tree"
- icon = 'icons/obj/flora/pinetrees.dmi'
- icon_state = "pine_1"
-
-/obj/structure/flora/tree/pine/New()
- ..()
- icon_state = "pine_[rand(1, 3)]"
-
-/obj/structure/flora/tree/pine/xmas
- name = "xmas tree"
- icon = 'icons/obj/flora/pinetrees.dmi'
- icon_state = "pine_c"
-
-/obj/structure/flora/tree/pine/xmas/New()
- ..()
- icon_state = "pine_c"
-
-/obj/structure/flora/tree/dead
- icon = 'icons/obj/flora/deadtrees.dmi'
- icon_state = "tree_1"
-
-/obj/structure/flora/tree/dead/New()
- ..()
- icon_state = "tree_[rand(1, 6)]"
-
-/obj/structure/flora/tree/sif
- name = "glowing tree"
- desc = "It's a tree, except this one seems quite alien. It glows a deep blue."
- icon = 'icons/obj/flora/deadtrees.dmi'
- icon_state = "tree_sif"
-
-/obj/structure/flora/tree/sif/New()
- update_icon()
-
-/obj/structure/flora/tree/sif/update_icon()
- set_light(5, 1, "#33ccff")
- overlays.Cut()
- overlays.Add(image(icon = 'icons/obj/flora/deadtrees.dmi', icon_state = "[icon_state]_glow", layer = LIGHTING_LAYER + 0.1))
-
-//grass
-/obj/structure/flora/grass
- name = "grass"
- icon = 'icons/obj/flora/snowflora.dmi'
- anchored = 1
-
-/obj/structure/flora/grass/brown
- icon_state = "snowgrass1bb"
-
-/obj/structure/flora/grass/brown/New()
- ..()
- icon_state = "snowgrass[rand(1, 3)]bb"
-/obj/structure/flora/grass/green
- icon_state = "snowgrass1gb"
-/obj/structure/flora/grass/green/New()
- ..()
- icon_state = "snowgrass[rand(1, 3)]gb"
-
-/obj/structure/flora/grass/both
- icon_state = "snowgrassall1"
-
-/obj/structure/flora/grass/both/New()
- ..()
- icon_state = "snowgrassall[rand(1, 3)]"
//bushes
diff --git a/code/game/objects/structures/flora/grass.dm b/code/game/objects/structures/flora/grass.dm
new file mode 100644
index 0000000000..d5e7e965a8
--- /dev/null
+++ b/code/game/objects/structures/flora/grass.dm
@@ -0,0 +1,27 @@
+//grass
+/obj/structure/flora/grass
+ name = "grass"
+ icon = 'icons/obj/flora/snowflora.dmi'
+ anchored = 1
+
+/obj/structure/flora/grass/brown
+ icon_state = "snowgrass1bb"
+
+/obj/structure/flora/grass/brown/New()
+ ..()
+ icon_state = "snowgrass[rand(1, 3)]bb"
+
+
+/obj/structure/flora/grass/green
+ icon_state = "snowgrass1gb"
+
+/obj/structure/flora/grass/green/New()
+ ..()
+ icon_state = "snowgrass[rand(1, 3)]gb"
+
+/obj/structure/flora/grass/both
+ icon_state = "snowgrassall1"
+
+/obj/structure/flora/grass/both/New()
+ ..()
+ icon_state = "snowgrassall[rand(1, 3)]"
\ No newline at end of file
diff --git a/code/game/objects/structures/flora/trees.dm b/code/game/objects/structures/flora/trees.dm
new file mode 100644
index 0000000000..d7960b5982
--- /dev/null
+++ b/code/game/objects/structures/flora/trees.dm
@@ -0,0 +1,202 @@
+//trees
+/obj/structure/flora/tree
+ name = "tree"
+ anchored = 1
+ density = 1
+ pixel_x = -16
+ layer = MOB_LAYER // You know what, let's play it safe.
+ var/base_state = null // Used for stumps.
+ var/health = 200 // Used for chopping down trees.
+ var/max_health = 200
+ var/shake_animation_degrees = 4 // How much to shake the tree when struck. Larger trees should have smaller numbers or it looks weird.
+ var/obj/item/stack/material/product = null // What you get when chopping this tree down. Generally it will be a type of wood.
+ var/product_amount = 10 // How much of a stack you get, if the above is defined.
+ var/is_stump = FALSE // If true, suspends damage tracking and most other effects.
+
+/obj/structure/flora/tree/attackby(var/obj/item/weapon/W, var/mob/living/user)
+ if(!istype(W))
+ return ..()
+
+ if(is_stump)
+ return
+
+ visible_message("\The [user] hits \the [src] with \the [W]!")
+
+ var/damage_to_do = W.force
+ if(!W.sharp && !W.edge)
+ damage_to_do = round(damage_to_do / 4)
+ if(damage_to_do > 0)
+ if(W.sharp && W.edge)
+ playsound(get_turf(src), 'sound/effects/woodcutting.ogg', 50, 1)
+ else
+ playsound(get_turf(src), W.hitsound, 50, 1)
+ if(damage_to_do > 5)
+ adjust_health(-damage_to_do)
+ else
+ to_chat(user, "\The [W] is ineffective at harming \the [src].")
+
+ hit_animation()
+ user.setClickCooldown(DEFAULT_ATTACK_COOLDOWN)
+ user.do_attack_animation(src)
+
+// Shakes the tree slightly, more or less stolen from lockers.
+/obj/structure/flora/tree/proc/hit_animation()
+ var/init_px = pixel_x
+ var/shake_dir = pick(-1, 1)
+ animate(src, transform=turn(matrix(), shake_animation_degrees * shake_dir), pixel_x=init_px + 2*shake_dir, time=1)
+ animate(transform=null, pixel_x=init_px, time=6, easing=ELASTIC_EASING)
+
+// Used when the tree gets hurt.
+/obj/structure/flora/tree/proc/adjust_health(var/amount)
+ if(is_stump)
+ return
+
+ health = between(0, health + amount, max_health)
+ if(health <= 0)
+ die()
+
+// Called when the tree loses all health, for whatever reason.
+/obj/structure/flora/tree/proc/die()
+ if(is_stump)
+ return
+
+ if(product && product_amount) // Make wooden logs.
+ var/obj/item/stack/material/M = new product(get_turf(src))
+ M.amount = product_amount
+ M.update_icon()
+ visible_message("\The [src] is felled!")
+ stump()
+
+// Makes the tree into a mostly non-interactive stump.
+/obj/structure/flora/tree/proc/stump()
+ if(is_stump)
+ return
+
+ is_stump = TRUE
+ icon_state = "[base_state]_stump"
+ overlays.Cut() // For the Sif tree and other future glowy trees.
+ set_light(0)
+
+/obj/structure/flora/tree/ex_act(var/severity)
+ adjust_health(-(max_health / severity))
+
+
+/obj/structure/flora/tree/get_description_interaction()
+ var/list/results = list()
+
+ if(!is_stump)
+ results += "[desc_panel_image("hatchet")]to cut down this tree into logs. Any sharp and strong weapon will do."
+
+ results += ..()
+
+ return results
+
+// Subtypes.
+
+// Pine trees
+
+/obj/structure/flora/tree/pine
+ name = "pine tree"
+ icon = 'icons/obj/flora/pinetrees.dmi'
+ icon_state = "pine_1"
+ base_state = "pine"
+ product = /obj/item/stack/material/log
+ shake_animation_degrees = 3
+
+/obj/structure/flora/tree/pine/New()
+ ..()
+ icon_state = "[base_state]_[rand(1, 3)]"
+
+
+/obj/structure/flora/tree/pine/xmas
+ name = "xmas tree"
+ icon = 'icons/obj/flora/pinetrees.dmi'
+ icon_state = "pine_c"
+
+/obj/structure/flora/tree/pine/xmas/New()
+ ..()
+ icon_state = "pine_c"
+
+// Palm trees
+
+/obj/structure/flora/tree/palm
+ icon = 'icons/obj/flora/palmtrees.dmi'
+ icon_state = "palm1"
+ base_state = "palm"
+ product = /obj/item/stack/material/log
+ product_amount = 5
+ health = 200
+ max_health = 200
+ pixel_x = 0
+
+/obj/structure/flora/tree/palm/New()
+ ..()
+ icon_state = "[base_state][rand(1, 2)]"
+
+
+// Dead trees
+
+/obj/structure/flora/tree/dead
+ icon = 'icons/obj/flora/deadtrees.dmi'
+ icon_state = "tree_1"
+ base_state = "tree"
+ product = /obj/item/stack/material/log
+ product_amount = 5
+ health = 200
+ max_health = 200
+
+/obj/structure/flora/tree/dead/New()
+ ..()
+ icon_state = "[base_state]_[rand(1, 6)]"
+
+// Small jungle trees
+
+/obj/structure/flora/tree/jungle_small
+ icon = 'icons/obj/flora/jungletreesmall.dmi'
+ icon_state = "tree"
+ base_state = "tree"
+ product = /obj/item/stack/material/log
+ product_amount = 10
+ health = 400
+ max_health = 400
+ pixel_x = -32
+
+/obj/structure/flora/tree/jungle_small/New()
+ ..()
+ icon_state = "[base_state][rand(1, 6)]"
+
+// Big jungle trees
+
+/obj/structure/flora/tree/jungle
+ icon = 'icons/obj/flora/jungletree.dmi'
+ icon_state = "tree"
+ base_state = "tree"
+ product = /obj/item/stack/material/log
+ product_amount = 20
+ health = 800
+ max_health = 800
+ pixel_x = -48
+ pixel_y = -16
+ shake_animation_degrees = 2
+
+/obj/structure/flora/tree/jungle/New()
+ ..()
+ icon_state = "[base_state][rand(1, 6)]"
+
+// Sif trees
+
+/obj/structure/flora/tree/sif
+ name = "glowing tree"
+ desc = "It's a tree, except this one seems quite alien. It glows a deep blue."
+ icon = 'icons/obj/flora/deadtrees.dmi'
+ icon_state = "tree_sif"
+ base_state = "tree_sif"
+ product = /obj/item/stack/material/log/sif
+
+/obj/structure/flora/tree/sif/New()
+ update_icon()
+
+/obj/structure/flora/tree/sif/update_icon()
+ set_light(5, 1, "#33ccff")
+ overlays.Cut()
+ overlays.Add(image(icon = 'icons/obj/flora/deadtrees.dmi', icon_state = "[icon_state]_glow", layer = LIGHTING_LAYER + 0.1))
\ No newline at end of file
diff --git a/code/game/turfs/simulated/outdoors/snow.dm b/code/game/turfs/simulated/outdoors/snow.dm
index 16678d7c98..22f9085a8c 100644
--- a/code/game/turfs/simulated/outdoors/snow.dm
+++ b/code/game/turfs/simulated/outdoors/snow.dm
@@ -25,7 +25,7 @@
/turf/simulated/floor/outdoors/snow/attackby(var/obj/item/W, var/mob/user)
if(istype(W, /obj/item/weapon/shovel))
to_chat(user, "You begin to remove \the [src] with your [W].")
- if(do_after(user, 4 SECONDS))
+ if(do_after(user, 4 SECONDS * W.toolspeed))
to_chat(user, "\The [src] has been dug up, and now lies in a pile nearby.")
new /obj/item/stack/material/snow(src)
demote()
diff --git a/code/game/turfs/simulated/wall_types.dm b/code/game/turfs/simulated/wall_types.dm
index 6b793d6061..ce4451ff12 100644
--- a/code/game/turfs/simulated/wall_types.dm
+++ b/code/game/turfs/simulated/wall_types.dm
@@ -53,6 +53,12 @@
/turf/simulated/wall/sifwood/New(var/newloc)
..(newloc,"alien wood")
+/turf/simulated/wall/log/New(var/newloc)
+ ..(newloc,"log")
+
+/turf/simulated/wall/log_sif/New(var/newloc)
+ ..(newloc,"alien log")
+
// Shuttle Walls
/turf/simulated/shuttle/wall
name = "autojoin wall"
diff --git a/code/modules/examine/stat_icons.dm b/code/modules/examine/stat_icons.dm
index b2ed64032a..1ece266f0c 100644
--- a/code/modules/examine/stat_icons.dm
+++ b/code/modules/examine/stat_icons.dm
@@ -29,4 +29,6 @@ var/global/list/description_icons = list(
"power cell" = image(icon='icons/obj/power.dmi',icon_state="hcell"),
"device cell" = image(icon='icons/obj/power.dmi',icon_state="dcell"),
"weapon cell" = image(icon='icons/obj/power.dmi',icon_state="wcell"),
+
+ "hatchet" = image(icon='icons/obj/weapons.dmi',icon_state="hatchet"),
)
diff --git a/code/modules/materials/material_recipes.dm b/code/modules/materials/material_recipes.dm
index ccda4fc9f6..c0c1eecd9e 100644
--- a/code/modules/materials/material_recipes.dm
+++ b/code/modules/materials/material_recipes.dm
@@ -139,6 +139,9 @@
recipes += new/datum/stack_recipe("wooden bucket", /obj/item/weapon/reagent_containers/glass/bucket/wood, 2, time = 4, one_per_turf = 0, on_floor = 0)
recipes += new/datum/stack_recipe("coilgun stock", /obj/item/weapon/coilgun_assembly, 5)
+/material/wood/log/generate_recipes()
+ return // Feel free to add log-only recipes here later if desired.
+
/material/cardboard/generate_recipes()
..()
recipes += new/datum/stack_recipe("box", /obj/item/weapon/storage/box)
diff --git a/code/modules/materials/material_sheets.dm b/code/modules/materials/material_sheets.dm
index 7ba518f6ef..f66d2425c6 100644
--- a/code/modules/materials/material_sheets.dm
+++ b/code/modules/materials/material_sheets.dm
@@ -203,6 +203,35 @@
icon_state = "sheet-wood"
default_type = "wood"
+/obj/item/stack/material/log
+ name = "log"
+ icon_state = "sheet-log"
+ default_type = "log"
+ no_variants = FALSE
+ color = "#824B28"
+ max_amount = 25
+ w_class = ITEMSIZE_HUGE
+
+/obj/item/stack/material/log/sif
+ name = "alien log"
+ color = "#0099cc"
+
+/obj/item/stack/material/log/attackby(var/obj/item/W, var/mob/user)
+ if(!istype(W))
+ return ..()
+ if(W.sharp && W.edge && use(1))
+ to_chat(user, "You cut up a log into planks.")
+ playsound(get_turf(src), 'sound/effects/woodcutting.ogg', 50, 1)
+ var/obj/item/stack/material/wood/existing_wood = locate() in user.loc
+ var/obj/item/stack/material/wood/new_wood = new(user.loc)
+ new_wood.amount = 2
+ if(existing_wood)
+ if(new_wood.transfer_to(existing_wood))
+ to_chat(user, "You add the newly-formed wood to the stack. It now contains [existing_wood.amount] planks.")
+ else
+ return ..()
+
+
/obj/item/stack/material/cloth
name = "cloth"
icon_state = "sheet-cloth"
diff --git a/code/modules/materials/materials.dm b/code/modules/materials/materials.dm
index 2daa7501c0..0db3a1016e 100644
--- a/code/modules/materials/materials.dm
+++ b/code/modules/materials/materials.dm
@@ -680,6 +680,18 @@ var/list/name_to_material
sheet_singular_name = "plank"
sheet_plural_name = "planks"
+/material/wood/log
+ name = "log"
+ icon_base = "log"
+ stack_type = /obj/item/stack/material/log
+ sheet_singular_name = "log"
+ sheet_plural_name = "logs"
+
+/material/wood/log/sif
+ name = "alien log"
+ icon_colour = "#0099cc" // Cyan-ish
+ stack_origin_tech = list(TECH_MATERIAL = 2, TECH_BIO = 2)
+
/material/wood/holographic
name = "holowood"
display_name = "wood"
diff --git a/code/modules/xenoarcheaology/finds/misc.dm b/code/modules/xenoarcheaology/finds/misc.dm
index 4037de5176..2729872876 100644
--- a/code/modules/xenoarcheaology/finds/misc.dm
+++ b/code/modules/xenoarcheaology/finds/misc.dm
@@ -6,10 +6,15 @@
name = "Crystal"
icon = 'icons/obj/mining.dmi'
icon_state = "crystal"
+ density = TRUE
+ anchored = TRUE
/obj/machinery/crystal/New()
if(prob(50))
icon_state = "crystal2"
+ set_light(3, 3, "#CC00CC")
+ else
+ set_light(3, 3, "#33CC33")
//large finds
/*
diff --git a/icons/obj/flora/deadtrees.dmi b/icons/obj/flora/deadtrees.dmi
index 2ae1a5a6e0..7a0b164619 100644
Binary files a/icons/obj/flora/deadtrees.dmi and b/icons/obj/flora/deadtrees.dmi differ
diff --git a/icons/obj/flora/jungleflora.dmi b/icons/obj/flora/jungleflora.dmi
new file mode 100644
index 0000000000..9a266e9226
Binary files /dev/null and b/icons/obj/flora/jungleflora.dmi differ
diff --git a/icons/obj/flora/jungletree.dmi b/icons/obj/flora/jungletree.dmi
new file mode 100644
index 0000000000..51f3141399
Binary files /dev/null and b/icons/obj/flora/jungletree.dmi differ
diff --git a/icons/obj/flora/jungletreesmall.dmi b/icons/obj/flora/jungletreesmall.dmi
new file mode 100644
index 0000000000..3abd375cc9
Binary files /dev/null and b/icons/obj/flora/jungletreesmall.dmi differ
diff --git a/icons/obj/flora/largejungleflora.dmi b/icons/obj/flora/largejungleflora.dmi
new file mode 100644
index 0000000000..bba0fd29f6
Binary files /dev/null and b/icons/obj/flora/largejungleflora.dmi differ
diff --git a/icons/obj/flora/palmtrees.dmi b/icons/obj/flora/palmtrees.dmi
new file mode 100644
index 0000000000..b8708b36d2
Binary files /dev/null and b/icons/obj/flora/palmtrees.dmi differ
diff --git a/icons/obj/flora/pinetrees.dmi b/icons/obj/flora/pinetrees.dmi
index 9ee04a5baf..63073046f0 100644
Binary files a/icons/obj/flora/pinetrees.dmi and b/icons/obj/flora/pinetrees.dmi differ
diff --git a/icons/obj/flora/rocks.dmi b/icons/obj/flora/rocks.dmi
index a1f6a0df0a..0974360e27 100644
Binary files a/icons/obj/flora/rocks.dmi and b/icons/obj/flora/rocks.dmi differ
diff --git a/icons/obj/stacks.dmi b/icons/obj/stacks.dmi
index 1713cacb67..5cdff4a1f3 100644
Binary files a/icons/obj/stacks.dmi and b/icons/obj/stacks.dmi differ
diff --git a/icons/turf/outdoors.dmi b/icons/turf/outdoors.dmi
index bcd81c28c9..31fab0ec95 100644
Binary files a/icons/turf/outdoors.dmi and b/icons/turf/outdoors.dmi differ
diff --git a/icons/turf/outdoors_edge.dmi b/icons/turf/outdoors_edge.dmi
index 02a52195c2..fb0b04168e 100644
Binary files a/icons/turf/outdoors_edge.dmi and b/icons/turf/outdoors_edge.dmi differ
diff --git a/icons/turf/wall_masks.dmi b/icons/turf/wall_masks.dmi
index 220e1b87e5..d67671c4d6 100644
Binary files a/icons/turf/wall_masks.dmi and b/icons/turf/wall_masks.dmi differ
diff --git a/polaris.dme b/polaris.dme
index 0bb468086a..657e0951f1 100644
--- a/polaris.dme
+++ b/polaris.dme
@@ -1043,6 +1043,8 @@
#include "code\game\objects\structures\crates_lockers\closets\secure\scientist.dm"
#include "code\game\objects\structures\crates_lockers\closets\secure\secure_closets.dm"
#include "code\game\objects\structures\crates_lockers\closets\secure\security.dm"
+#include "code\game\objects\structures\flora\grass.dm"
+#include "code\game\objects\structures\flora\trees.dm"
#include "code\game\objects\structures\ghost_pods\ghost_pods.dm"
#include "code\game\objects\structures\ghost_pods\silicon.dm"
#include "code\game\objects\structures\stool_bed_chair_nest\alien_nests.dm"