mirror of
https://github.com/Aurorastation/Aurora.3.git
synced 2025-12-22 16:12:19 +00:00
Merge pull request #11265 from Karolis2011/camera_fix
General camera fixes.
This commit is contained in:
@@ -181,3 +181,8 @@
|
|||||||
#define COLOR_PALE_RED_GRAY "#CC9090"
|
#define COLOR_PALE_RED_GRAY "#CC9090"
|
||||||
#define COLOR_PALE_PURPLE_GRAY "#BDA2BA"
|
#define COLOR_PALE_PURPLE_GRAY "#BDA2BA"
|
||||||
#define COLOR_PURPLE_GRAY "#A2819E"
|
#define COLOR_PURPLE_GRAY "#A2819E"
|
||||||
|
|
||||||
|
//Camera capture modes
|
||||||
|
#define CAPTURE_MODE_REGULAR 0 //Regular polaroid camera mode
|
||||||
|
#define CAPTURE_MODE_ALL 1 //Admin camera mode
|
||||||
|
#define CAPTURE_MODE_PARTIAL 3 //Simular to regular mode, but does not do dummy check
|
||||||
|
|||||||
@@ -760,7 +760,11 @@ proc // Creates a single icon from a given /atom or /image. Only the first argu
|
|||||||
// Pull the default direction.
|
// Pull the default direction.
|
||||||
add = icon(I:icon, I:icon_state)
|
add = icon(I:icon, I:icon_state)
|
||||||
else // 'I' is an appearance object.
|
else // 'I' is an appearance object.
|
||||||
add = getFlatIcon(new/image(I), curdir, curicon, curstate, curblend)
|
if(istype(A,/obj/machinery/atmospherics) && I in A.underlays)
|
||||||
|
var/image/Im = I
|
||||||
|
add = getFlatIcon(new/image(I), Im.dir, curicon, curstate, curblend, 1)
|
||||||
|
else
|
||||||
|
add = getFlatIcon(new/image(I), curdir, curicon, curstate, curblend, always_use_defdir)
|
||||||
|
|
||||||
// Find the new dimensions of the flat icon to fit the added overlay
|
// Find the new dimensions of the flat icon to fit the added overlay
|
||||||
addX1 = min(flatX1, I:pixel_x+1)
|
addX1 = min(flatX1, I:pixel_x+1)
|
||||||
@@ -773,9 +777,15 @@ proc // Creates a single icon from a given /atom or /image. Only the first argu
|
|||||||
flat.Crop(addX1-flatX1+1, addY1-flatY1+1, addX2-flatX1+1, addY2-flatY1+1)
|
flat.Crop(addX1-flatX1+1, addY1-flatY1+1, addX2-flatX1+1, addY2-flatY1+1)
|
||||||
flatX1=addX1;flatX2=addX2
|
flatX1=addX1;flatX2=addX2
|
||||||
flatY1=addY1;flatY2=addY2
|
flatY1=addY1;flatY2=addY2
|
||||||
|
var/iconmode
|
||||||
|
if(I in A.overlays)
|
||||||
|
iconmode = ICON_OVERLAY
|
||||||
|
else if(I in A.underlays)
|
||||||
|
iconmode = ICON_UNDERLAY
|
||||||
|
else
|
||||||
|
iconmode = blendMode2iconMode(curblend)
|
||||||
// Blend the overlay into the flattened icon
|
// Blend the overlay into the flattened icon
|
||||||
flat.Blend(add, blendMode2iconMode(curblend), I:pixel_x + 2 - flatX1, I:pixel_y + 2 - flatY1)
|
flat.Blend(add, iconmode, I:pixel_x + 2 - flatX1, I:pixel_y + 2 - flatY1)
|
||||||
|
|
||||||
if(A.color)
|
if(A.color)
|
||||||
flat.Blend(A.color, ICON_MULTIPLY)
|
flat.Blend(A.color, ICON_MULTIPLY)
|
||||||
@@ -853,3 +863,53 @@ proc/sort_atoms_by_layer(var/list/atoms)
|
|||||||
result.Swap(i, gap + i)
|
result.Swap(i, gap + i)
|
||||||
swapped = 1
|
swapped = 1
|
||||||
return result
|
return result
|
||||||
|
/*
|
||||||
|
generate_image function generates image of specified range and location
|
||||||
|
arguments tx, ty, tz are target coordinates (requred), range defines render distance to opposite corner (requred)
|
||||||
|
cap_mode is capturing mode (optional), user is capturing mob (requred only wehen cap_mode = CAPTURE_MODE_REGULAR),
|
||||||
|
lighting determines lighting capturing (optional), suppress_errors suppreses errors and continues to capture (optional).
|
||||||
|
*/
|
||||||
|
proc/generate_image(var/tx as num, var/ty as num, var/tz as num, var/range as num, var/cap_mode = CAPTURE_MODE_PARTIAL, var/mob/living/user, var/lighting = 1, var/suppress_errors = 1)
|
||||||
|
var/list/turfstocapture = list()
|
||||||
|
//Lines below determine what tiles will be rendered
|
||||||
|
for(var/xoff = 0 to range)
|
||||||
|
for(var/yoff = 0 to range)
|
||||||
|
var/turf/T = locate(tx + xoff,ty + yoff,tz)
|
||||||
|
if(T)
|
||||||
|
if(cap_mode == CAPTURE_MODE_REGULAR)
|
||||||
|
if(user.can_capture_turf(T))
|
||||||
|
turfstocapture.Add(T)
|
||||||
|
continue
|
||||||
|
else
|
||||||
|
turfstocapture.Add(T)
|
||||||
|
else
|
||||||
|
//Capture includes non-existan turfs
|
||||||
|
if(!suppress_errors)
|
||||||
|
return
|
||||||
|
//Lines below determine what objects will be rendered
|
||||||
|
var/list/atoms = list()
|
||||||
|
for(var/turf/T in turfstocapture)
|
||||||
|
atoms.Add(T)
|
||||||
|
for(var/atom/A in T)
|
||||||
|
if(istype(A, /atom/movable/lighting_overlay) && lighting) //Special case for lighting
|
||||||
|
atoms.Add(A)
|
||||||
|
continue
|
||||||
|
if(A.invisibility) continue
|
||||||
|
atoms.Add(A)
|
||||||
|
//Lines below actually render all colected data
|
||||||
|
atoms = sort_atoms_by_layer(atoms)
|
||||||
|
var/icon/cap = icon('icons/effects/96x96.dmi', "")
|
||||||
|
cap.Scale(range*32, range*32)
|
||||||
|
cap.Blend("#000", ICON_OVERLAY)
|
||||||
|
for(var/atom/A in atoms)
|
||||||
|
if(A)
|
||||||
|
var/icon/img = getFlatIcon(A)
|
||||||
|
if(istype(img, /icon))
|
||||||
|
if(istype(A, /mob/living) && A:lying)
|
||||||
|
img.BecomeLying()
|
||||||
|
var/xoff = (A.x - tx) * 32
|
||||||
|
var/yoff = (A.y - ty) * 32
|
||||||
|
cap.Blend(img, blendMode2iconMode(A.blend_mode), A.pixel_x + xoff, A.pixel_y + yoff)
|
||||||
|
|
||||||
|
return cap
|
||||||
|
|
||||||
|
|||||||
@@ -4,6 +4,7 @@
|
|||||||
set desc = "Usage: Capture-Map-Part target_x_cord target_y_cord target_z_cord range (captures part of a map originating from bottom left corner)"
|
set desc = "Usage: Capture-Map-Part target_x_cord target_y_cord target_z_cord range (captures part of a map originating from bottom left corner)"
|
||||||
|
|
||||||
if(!check_rights(R_ADMIN|R_DEBUG|R_SERVER))
|
if(!check_rights(R_ADMIN|R_DEBUG|R_SERVER))
|
||||||
|
usr << "You are not allowed to use this command"
|
||||||
return
|
return
|
||||||
|
|
||||||
if(isnull(tx) || isnull(ty) || isnull(tz) || isnull(range))
|
if(isnull(tx) || isnull(ty) || isnull(tz) || isnull(range))
|
||||||
@@ -17,41 +18,7 @@
|
|||||||
return
|
return
|
||||||
|
|
||||||
if(locate(tx,ty,tz))
|
if(locate(tx,ty,tz))
|
||||||
var/list/turfstocapture = list()
|
var/cap = generate_image(tx ,ty ,tz ,range, CAPTURE_MODE_PARTIAL, null, 1, 1)
|
||||||
var/hasasked = 0
|
|
||||||
for(var/xoff = 0 to range)
|
|
||||||
for(var/yoff = 0 to range)
|
|
||||||
var/turf/T = locate(tx + xoff,ty + yoff,tz)
|
|
||||||
if(T)
|
|
||||||
turfstocapture.Add(T)
|
|
||||||
else
|
|
||||||
if(!hasasked)
|
|
||||||
var/answer = alert("Capture includes non existant turf, Continue capture?","Continue capture?", "No", "Yes")
|
|
||||||
hasasked = 1
|
|
||||||
if(answer == "No")
|
|
||||||
return
|
|
||||||
|
|
||||||
var/list/atoms = list()
|
|
||||||
for(var/turf/T in turfstocapture)
|
|
||||||
atoms.Add(T)
|
|
||||||
for(var/atom/A in T)
|
|
||||||
if(A.invisibility) continue
|
|
||||||
atoms.Add(A)
|
|
||||||
|
|
||||||
atoms = sort_atoms_by_layer(atoms)
|
|
||||||
var/icon/cap = icon('icons/effects/96x96.dmi', "")
|
|
||||||
cap.Scale(range*32, range*32)
|
|
||||||
cap.Blend("#000", ICON_OVERLAY)
|
|
||||||
for(var/atom/A in atoms)
|
|
||||||
if(A)
|
|
||||||
var/icon/img = getFlatIcon(A)
|
|
||||||
if(istype(img, /icon))
|
|
||||||
if(istype(A, /mob/living) && A:lying)
|
|
||||||
img.BecomeLying()
|
|
||||||
var/xoff = (A.x - tx) * 32
|
|
||||||
var/yoff = (A.y - ty) * 32
|
|
||||||
cap.Blend(img, blendMode2iconMode(A.blend_mode), A.pixel_x + xoff, A.pixel_y + yoff)
|
|
||||||
|
|
||||||
var/file_name = "map_capture_x[tx]_y[ty]_z[tz]_r[range].png"
|
var/file_name = "map_capture_x[tx]_y[ty]_z[tz]_r[range].png"
|
||||||
usr << "Saved capture in cache as [file_name]."
|
usr << "Saved capture in cache as [file_name]."
|
||||||
usr << browse_rsc(cap, file_name)
|
usr << browse_rsc(cap, file_name)
|
||||||
|
|||||||
@@ -165,55 +165,6 @@ var/global/photo_count = 0
|
|||||||
..()
|
..()
|
||||||
|
|
||||||
|
|
||||||
/obj/item/device/camera/proc/get_icon(list/turfs, turf/center)
|
|
||||||
|
|
||||||
//Bigger icon base to capture those icons that were shifted to the next tile
|
|
||||||
//i.e. pretty much all wall-mounted machinery
|
|
||||||
var/icon/res = icon('icons/effects/96x96.dmi', "")
|
|
||||||
res.Scale(size*32, size*32)
|
|
||||||
// Initialize the photograph to black.
|
|
||||||
res.Blend("#000", ICON_OVERLAY)
|
|
||||||
|
|
||||||
var/atoms[] = list()
|
|
||||||
for(var/turf/the_turf in turfs)
|
|
||||||
// Add outselves to the list of stuff to draw
|
|
||||||
atoms.Add(the_turf);
|
|
||||||
// As well as anything that isn't invisible.
|
|
||||||
for(var/atom/A in the_turf)
|
|
||||||
if(A.invisibility) continue
|
|
||||||
atoms.Add(A)
|
|
||||||
|
|
||||||
// Sort the atoms into their layers
|
|
||||||
var/list/sorted = sort_atoms_by_layer(atoms)
|
|
||||||
var/center_offset = (size-1)/2 * 32 + 1
|
|
||||||
for(var/i; i <= sorted.len; i++)
|
|
||||||
var/atom/A = sorted[i]
|
|
||||||
if(A)
|
|
||||||
var/icon/img = getFlatIcon(A)//build_composite_icon(A)
|
|
||||||
|
|
||||||
// If what we got back is actually a picture, draw it.
|
|
||||||
if(istype(img, /icon))
|
|
||||||
// Check if we're looking at a mob that's lying down
|
|
||||||
if(istype(A, /mob/living) && A:lying)
|
|
||||||
// If they are, apply that effect to their picture.
|
|
||||||
img.BecomeLying()
|
|
||||||
// Calculate where we are relative to the center of the photo
|
|
||||||
var/xoff = (A.x - center.x) * 32 + center_offset
|
|
||||||
var/yoff = (A.y - center.y) * 32 + center_offset
|
|
||||||
if (istype(A,/atom/movable))
|
|
||||||
xoff+=A:step_x
|
|
||||||
yoff+=A:step_y
|
|
||||||
res.Blend(img, blendMode2iconMode(A.blend_mode), A.pixel_x + xoff, A.pixel_y + yoff)
|
|
||||||
|
|
||||||
// Lastly, render any contained effects on top.
|
|
||||||
for(var/turf/the_turf in turfs)
|
|
||||||
// Calculate where we are relative to the center of the photo
|
|
||||||
var/xoff = (the_turf.x - center.x) * 32 + center_offset
|
|
||||||
var/yoff = (the_turf.y - center.y) * 32 + center_offset
|
|
||||||
res.Blend(getFlatIcon(the_turf.loc), blendMode2iconMode(the_turf.blend_mode),xoff,yoff)
|
|
||||||
return res
|
|
||||||
|
|
||||||
|
|
||||||
/obj/item/device/camera/proc/get_mobs(turf/the_turf as turf)
|
/obj/item/device/camera/proc/get_mobs(turf/the_turf as turf)
|
||||||
var/mob_detail
|
var/mob_detail
|
||||||
for(var/mob/living/carbon/A in the_turf)
|
for(var/mob/living/carbon/A in the_turf)
|
||||||
@@ -248,37 +199,39 @@ var/global/photo_count = 0
|
|||||||
icon_state = icon_on
|
icon_state = icon_on
|
||||||
on = 1
|
on = 1
|
||||||
|
|
||||||
/obj/item/device/camera/proc/can_capture_turf(turf/T, mob/user)
|
//Proc for capturing check
|
||||||
|
/mob/living/proc/can_capture_turf(turf/T)
|
||||||
var/mob/dummy = new(T) //Go go visibility check dummy
|
var/mob/dummy = new(T) //Go go visibility check dummy
|
||||||
var/viewer = user
|
var/viewer = src
|
||||||
if(user.client) //To make shooting through security cameras possible
|
if(src.client) //To make shooting through security cameras possible
|
||||||
viewer = user.client.eye
|
viewer = src.client.eye
|
||||||
var/can_see = (dummy in viewers(world.view, viewer))
|
var/can_see = (dummy in viewers(world.view, viewer))
|
||||||
|
|
||||||
qdel(dummy)
|
qdel(dummy)
|
||||||
return can_see
|
return can_see
|
||||||
|
|
||||||
/obj/item/device/camera/proc/captureimage(atom/target, mob/user, flag)
|
/obj/item/device/camera/proc/captureimage(atom/target, mob/living/user, flag)
|
||||||
var/x_c = target.x - (size-1)/2
|
var/x_c = target.x - (size-1)/2
|
||||||
var/y_c = target.y + (size-1)/2
|
var/y_c = target.y + (size-1)/2
|
||||||
var/z_c = target.z
|
var/z_c = target.z
|
||||||
var/list/turfs = list()
|
|
||||||
var/mobs = ""
|
var/mobs = ""
|
||||||
for(var/i = 1; i <= size; i++)
|
for(var/i = 1; i <= size; i++)
|
||||||
for(var/j = 1; j <= size; j++)
|
for(var/j = 1; j <= size; j++)
|
||||||
var/turf/T = locate(x_c, y_c, z_c)
|
var/turf/T = locate(x_c, y_c, z_c)
|
||||||
if(can_capture_turf(T, user))
|
if(user.can_capture_turf(T))
|
||||||
turfs.Add(T)
|
|
||||||
mobs += get_mobs(T)
|
mobs += get_mobs(T)
|
||||||
x_c++
|
x_c++
|
||||||
y_c--
|
y_c--
|
||||||
x_c = x_c - size
|
x_c = x_c - size
|
||||||
|
|
||||||
var/obj/item/weapon/photo/p = createpicture(target, user, turfs, mobs, flag)
|
var/obj/item/weapon/photo/p = createpicture(target, user, mobs, flag)
|
||||||
printpicture(user, p)
|
printpicture(user, p)
|
||||||
|
|
||||||
/obj/item/device/camera/proc/createpicture(atom/target, mob/user, list/turfs, mobs, flag)
|
/obj/item/device/camera/proc/createpicture(atom/target, mob/user, mobs, flag)
|
||||||
var/icon/photoimage = get_icon(turfs, target)
|
var/x_c = target.x - (size-1)/2
|
||||||
|
var/y_c = target.y - (size-1)/2
|
||||||
|
var/z_c = target.z
|
||||||
|
var/icon/photoimage = generate_image(x_c, y_c, z_c, size, CAPTURE_MODE_REGULAR, user)
|
||||||
|
|
||||||
var/icon/small_img = icon(photoimage)
|
var/icon/small_img = icon(photoimage)
|
||||||
var/icon/tiny_img = icon(photoimage)
|
var/icon/tiny_img = icon(photoimage)
|
||||||
|
|||||||
@@ -69,8 +69,9 @@
|
|||||||
aipictures -= selection
|
aipictures -= selection
|
||||||
usr << "<span class='unconscious'>Local image deleted</span>"
|
usr << "<span class='unconscious'>Local image deleted</span>"
|
||||||
|
|
||||||
/obj/item/device/camera/siliconcam/ai_camera/can_capture_turf(turf/T, mob/user)
|
//Capture Proc for AI / Robot
|
||||||
var/mob/living/silicon/ai = user
|
/mob/living/silicon/ai/can_capture_turf(turf/T)
|
||||||
|
var/mob/living/silicon/ai = src
|
||||||
return ai.TurfAdjacent(T)
|
return ai.TurfAdjacent(T)
|
||||||
|
|
||||||
/obj/item/device/camera/siliconcam/proc/toggle_camera_mode()
|
/obj/item/device/camera/siliconcam/proc/toggle_camera_mode()
|
||||||
|
|||||||
Reference in New Issue
Block a user