ID:2121243
 
(See the best response by Nadrew.)
My current project is suffering from horrendous client lag. I will explain some details to see if I can bring forth any thoughts or suggestions.

1) Many of my players are being forced to disconnect, or dream seeker will just crash.
2) Periodically, dream seeker will slow down or lag for the individual while CPU is extremely low.
3) After experiencing a lag or a client delay, and reconnecting to the game within that same dream seeker, the lag/delay still exist.

I have no leads to pinpointing the following issues, can you suggestion any debugging methods/strategies to help me uncover this problem.

#define DEBUG

Check the profiles on DS.
Isn't that the same as having generate debug information On in preferences?
Sounds like an infinite loop possibly?
In response to Fat Albert
Indeed it is.
In response to Wicked Games Inc
Possibly. the thing is, it isn't cpu driven. Its not server side as far as I can tell. Its only the individual who is a effected, everyone else is experiencing smooth gameplay. I thinking there some sort of background resource build. The weirdest part is if someone reconnects they experience the same horrible experience, but if they open up a completely different dream seeker its smooth. I think this particular dynamic is a key to pinpoint possible causes. I just don't know all of what goes on behind the scene of the BYOND engine so am not able to identify potential causes.
Best response
Sounds like something is forcing the client into software rendering mode, or something along those lines. Next time a client reports it, have them toggle the rendering mode from software back to hardware to see if it clears up.

If that does it, you need to figure out where the problem comes from, things like transparent interface window elements and graphical effects that specific GPU drivers don't support will cause DirectX to bail out.
Sadly that was not the issue, i started playing with it software rendering off and still ran into the same issue of client lag
The question is whether the lag persists after it begins if you disabled hardware rendering and enable it again from the client menu of the Options and Messages window. If something is forcing it into software mode you'd be able to tell by switching it back.
I have a feeling it's how you're doing your minimap system.
How're you handling it code-wise?
Okay can you give us some more information here? I've done a lot of optimizations including clientside optimization but we really can only guess without knowing more.

Typical client view size
Number of client images in a typical client at time of slowdown
Number of screen objects in a typical client at time of slowdown
Number of objects on screen at time of slowdown
How many overlays/underlays do any of the above normally have?

If you can reliably reproduce the clientside lag then you should be able to write some very simple looping functions to count all those for your client using view(). But this is primarily to establish that you have a sane number of objects being rendered by DS at any time and is really just a small start to diagnosing your problem.

You can gather all this information with a simple function like:
client/verb/clientside_profile()
var/atoms = 0
var/overlays = 0
var/underlays = 0

for(var/atom/A in view())
atoms++
overlays += A.overlays.len
underlays += A.underlays.len

var/screenobj = screen.len
var/screenobjoverlays = 0
var/screenobjunderlays = 0

for(var/atom/A in screen)
screenobjoverlays += A.overlays.len
screenobjunderlays += A.underlays.len

var/images = images.len
var/imagesunderlays = 0
var/imagesoverlays = 0

for(var/image/I in images)
imagesoverlays += I.overlays.len
imagesunderlays += I.underlays.len

//Add some code to store the gathered information above somewhere or send it to the client

Though I can't say I'm sure if you might want to have a function that recursive counts, but I suppose if you're just trying to establish that you have a sane value something simple like this would do.

Now there have been a few recent new features that can cause client side latency when used in certain ways, most older byond features have never presented this problem because so little used to be done on the client side.

Are you using KEEP_TOGETHER a lot?
Are you using PLANE_MASTERs a lot?

Both of the above have personally been the source of any mysterious clientside latency that I've had in the past.

Please note: the issue that I have previously had with plane masters SHOULD currently be fixed, however you may have found a nonstandard case in which it is could be causing problems.
Yeah the only PLANE MASTER code I have is the minimap code. I'm going to disable it for the time being and see if it gets rid of the issue. Ill report my findings, until then feel free to analyze the code.

var/list/minimap=new
var/maprendering=0
proc
TPixelGet1(bypass=0)//Call at world New(), This a minimap of all maps
set waitfor=FALSE
set background=1
if(!LoadMiniMap()||bypass)//Checks if theres a previous minimap icon that can be loaded
world<<"Creating World MiniMap"
for(var/p in typesof(/turf))//This loop creates the miniture version of all turfs in game so can be used for
if(p in list(/turf,/turf/Othernewturf/Density))
else
var/turf/t=new p(locate(1,1,1))
var/icon/i=icon(t.icon,t.icon_state)
if(t.icon==null||!i.GetPixel(i.Width()/2,i.Height()/2)||i==null)
continue
var/scalex=i.Width()/32
var/scaley=i.Height()/32
if(scalex<1) scalex=(1-scalex)*15
if(scaley<1) scaley=(1-scaley)*15
i.Scale(scalex,scaley)
minimap[t.type]=i
for(var/p in typesof(/obj))//This loop creates the miniture version of all objs in game so can be used for
if(p in list(/obj,/obj/Test))
else//Skip certain items
if(ispath(p,/obj/Missions)||ispath(p,/obj/Items)||ispath(p,/obj/FTCS_Object)||ispath(p,/obj/Vehicles)||ispath(p,/obj/Overlays)||ispath(p,/obj/Hud)||ispath(p,/obj/Effects)||ispath(p,/obj/CreatureSpawns)||ispath(p, /obj/Spawns)||ispath(p,/obj/Projectiles)||ispath(p,/obj/Background)||ispath(p, /obj/SkillTree)||ispath(p, /obj/Mission)||ispath(p,/obj/DeathPrompts)||ispath(p,/obj/Training/Laps)) continue
var/obj/t=new p
var/icon/i=icon(t.icon,t.icon_state)
var/scalex=i.Width()/32
var/scaley=i.Height()/32
if(scalex<1) scalex=(1-scalex)*15
if(scaley<1) scaley=(1-scaley)*15
i.Scale(scalex,scaley)
minimap[t.type]=i
world<<"Rendering World Map"
var/icon/lastimage
world<<"Turfs..."
for(var/turf/T in world)//This loop puts all the minimap turfs together
if(maprendering!=T.z)
maprendering=T.z
world<<"Turf Map [maprendering]"
if(T.type==/turf) continue
var/icon/worldicon=wholemap[T.z]
if(!wholemap[T.z])
wholemap[T.z]=new/icon('blank2.dmi')
var/sizex=world.maxx
var/sizey=world.maxy
worldicon=wholemap[T.z]
worldicon.Scale(sizex,sizey)
var/imageobj=minimap[T.type]
if(!isicon(imageobj))//If no icon for turf we will just use the last icon found
imageobj=lastimage
else lastimage=imageobj
if(imageobj) worldicon.Blend(imageobj,ICON_OVERLAY,T.x,T.y)
if(T.x==world.maxx&&T.y%2==0)//Incrementally sleep so game doesn't completely pause while rendering
sleep(1)
world<<"objs..."
maprendering=0
for(var/obj/T in world)//Same as turfs but for objects
if(istype(T,/obj/Missions)||istype(T,/obj/Items)||istype(T,/obj/FTCS_Object)||istype(T,/obj/Vehicles)||istype(T,/obj/Overlays)||istype(T,/obj/Hud)||istype(T,/obj/Effects)||istype(T,/obj/CreatureSpawns)||istype(T, /obj/Spawns)||istype(T,/obj/Projectiles)||istype(T,/obj/Background)||istype(T, /obj/SkillTree)||istype(T, /obj/Mission)||istype(T,/obj/DeathPrompts)||istype(T,/obj/Training/Laps)) continue
if(maprendering!=T.z)
maprendering=T.z
world<<"Objs Map [maprendering]"
if(T.z==0) continue
var/icon/worldicon=wholemap[T.z]
var/imageobj=minimap[T.type]
if(!isicon(imageobj))
imageobj=lastimage
sleep(1)
else lastimage=imageobj
if(imageobj) worldicon.Blend(imageobj,ICON_OVERLAY,T.x,T.y)
if(T.x%(world.maxx)==0)
sleep(rand(0,1))
world<<"Saving World MiniMap"
SaveMiniMap()
var/list/wholemap[world.maxz]
var/mastersx=2
var/mastersy=17
var/masterpx=1
var/masterpy=1
var/mpx=22
var/mpy=22
mob
var
obj
tmp
worldmap//Each player need a copy of the world map since each image will be shifting depend on the players location
planemaster//defined to display allys/enemy objects on it
obj
WorldMap
blend_mode = BLEND_MULTIPLY
plane = 2
layer=4
proc
ChangeIcon(mob/O)//Function called when player moves to make minimap move
set waitfor=FALSE
if(O&&wholemap.len>=O.z&&O.z)
src.icon=wholemap[O.z]
var/icon/worldicon=wholemap[1]
if(worldicon)
var/sx=1
var/sy=1
var/px=mastersx*32+masterpx-O.x+1
var/py=mastersy*32+masterpy-O.y
screen_loc="[sx]:[px+mpx],[sy]:[py+mpy]"
obj/minimap_plane//Master Plane
plane = 2
blend_mode = BLEND_DEFAULT
appearance_flags = PLANE_MASTER | NO_CLIENT_COLOR
mouse_opacity = 0
New()
..()
screen_loc = "[mastersx]:[masterpx],[mastersy]:[masterpy]"
image/visiblearea
plane = 2
blend_mode = BLEND_ADD
icon = 'blank.dmi'//White icon crops minimap(Visible Area of minimap)
icon_state="white"
image/border
plane = 2
blend_mode = BLEND_ADD
icon = 'blank.dmi' //Gives minimap a circular black border
icon_state="black"
You should define variables outside of the loops if you can so you're not constantly creating variables.
That's not really relevant to this though, also have you ever actually profiled that one?
So there were no apparently improvements from removing the minimap code. But since the code is posted, I want to ask a question about it. The visible area dictates which area of the minimap icon the client will see. It has to be white for the BLEND_MULTIPLY to make only that area visible. The problem is, so I get to the edge of the map where there is no minimap icon, it shows up white because of the visible area background. Do you know of a way I can make it black?
So in the game. The statpanel and chatbox are separate windows and has a faint transparency. I will be removing that transparency and will note any improvements.
In response to Nadrew
Yes, I did that aswell Nadrew. I was just sharing another scenario I tried with the software rendering mode. From my tests it has had no effect on the client lag/delay.
In response to Fat Albert
Fat Albert wrote:
So in the game. The statpanel and chatbox are separate windows and has a faint transparency. I will be removing that transparency and will note any improvements.

That would force it into software rendering mode. Hardware rendering mode doesn't support transparent windows. In software mode you'll notice a dramatic slowdown compared to hardware rendering mode. Your game has been running in software mode since those windows were added.

Couple software mode with PLANE_MASTER and I figure that's your lag culprit.
Yeah it seems it was the transparent windows, everything is smooth even with the plane master minimap! Should this be reported to fixed, so others don't run into the same problem. Why make transparent windows an option if its not supported. I've been using transparent chatboxes since 2012 when I developed Star Wars Evolution. Its kind of awkward I'm just finding this out.
Page: 1 2