local function m(m)local W=m.Tags if W then for m,W in pairs(W)do if W=="\068\101\112\114\101\099\097\116\101\100"or W=="\072\105\100\100\101\110"or W=="\082\101\097\100\079\110\108\121"or W=="\078\111\116\083\099\114\105\112\116\097\098\108\101"then return true end end end return false end function Set(m,W,h)local o=W.Name local D=W.ValueType if h==nil then return end for m,D in pairs(GetSelection())do if CanEditProperty(D,W)then pcall(function()D[o]=h RemoteEvent:InvokeServer("\083\101\116\080\114\111\112\101\114\116\121",D,o,h)end)end end end function CreateRow(m,W,h)local o=W.Name local D=m[o]local s=Row.BackgroundColor if h then s=Row.BackgroundColorAlternate end local p=not CanEditProperty(m,W)local c=Instance.new("\070\114\097\109\101")c.Size=UDim2.new(1,0,0,Row.Height)c.BackgroundTransparency=1 c.Name="\082\111\119"local Q=CreateCell()Q.Parent=c Q.ClipsDescendants=true local K=CreateLabel(p)K.Text=o K.Size=UDim2.new(1,-1*Row.TitleMarginLeft,1,0)K.Position=UDim2.new(0,Row.TitleMarginLeft,0,0)K.Parent=Q local t=CreateCell()t.Size=UDim2.new(.5,-1,1,0)t.Position=UDim2.new(.5,0,0,0)t.Parent=c local g=GetControl(m,W,p)g.Parent=t c.MouseEnter:connect(function()Q.BackgroundColor3=Row.BackgroundColorMouseover t.BackgroundColor3=Row.BackgroundColorMouseover end)c.MouseLeave:connect(function()Q.BackgroundColor3=s t.BackgroundColor3=s end)Q.BackgroundColor3=s t.BackgroundColor3=s return c end function ClearPropertiesList()for m,W in pairs(ContentFrame:GetChildren())do W:Destroy()end end local W=Gui:FindFirstChild("\083\101\108\101\099\116\105\111\110",1)function displayProperties(m)for m,W in pairs(m)do pcall(function()local m=CreateRow(W.object,W.propertyData,numRows%2==0)m.Position=UDim2.new(0,0,0,numRows*Row.Height)m.Parent=ContentFrame numRows=numRows+1 end)end end function checkForDupe(m,W)for W,h in pairs(W)do if h.propertyData.Name==m.Name and(h.propertyData.ValueType.Category==m.ValueType.Category and h.propertyData.ValueType.Name==m.ValueType.Name)then return true end end return false end function sortProps(m)table.sort(m,function(m,W)return m.propertyData.Name<W.propertyData.Name end)end function showProperties(W)ClearPropertiesList()if W==nil then return end local h={}local o={}numRows=0 for W,D in pairs(W)do if not o[D.className]then o[D.className]=true for W,o in pairs(RbxApi.GetProperties(D.className))do local s,p=pcall(function()if not m(o)and not checkForDupe(o,h)then if string.find(string.lower(o.Name),string.lower(propertiesSearch.Text))or not searchingProperties()then table.insert(h,{propertyData=o,object=D})end end end)end end end sortProps(h)displayProperties(h)ContentFrame.Size=UDim2.new(1,0,0,numRows*Row.Height)scrollBar.ScrollIndex=0 scrollBar.TotalSpace=numRows*Row.Height scrollBar.Update()end

local function PropertyIsHidden(propertyData)
	local tags = propertyData["Tags"]
	if tags then
		for _,name in pairs(tags) do
			if name == "Deprecated" or name == "Hidden" or name == "ReadOnly" or name == "NotScriptable" then
				return true
			end
		end
	end
	return false
end

function Set(object, propertyData, value)
	local propertyName = propertyData["Name"]
	local propertyType = propertyData["ValueType"]

	if value == nil then return end

	for i,v in pairs(GetSelection()) do
		if CanEditProperty(v,propertyData) then
			pcall(function()
				--print("Setting " .. propertyName .. " to " .. tostring(value))
				v[propertyName] = value
				RemoteEvent:InvokeServer("SetProperty", v, propertyName, value)
			end)
		end
	end

end

function CreateRow(object, propertyData, isAlternateRow)
	local propertyName = propertyData["Name"]
	local propertyValue = object[propertyName]
	--rowValue, rowValueType, isAlternate
	local backColor = Row.BackgroundColor;
	if (isAlternateRow) then
		backColor = Row.BackgroundColorAlternate
	end

	local readOnly = not CanEditProperty(object, propertyData)
	--if propertyType == "Instance" or propertyName == "Parent" then readOnly = true end

	local rowFrame = Instance.new("Frame")
	rowFrame.Size = UDim2.new(1,0,0,Row.Height)
	rowFrame.BackgroundTransparency = 1
	rowFrame.Name = 'Row'

	local propertyLabelFrame = CreateCell()
	propertyLabelFrame.Parent = rowFrame
	propertyLabelFrame.ClipsDescendants = true

	local propertyLabel = CreateLabel(readOnly)
	propertyLabel.Text = propertyName
	propertyLabel.Size = UDim2.new(1, -1 * Row.TitleMarginLeft, 1, 0)
	propertyLabel.Position = UDim2.new(0, Row.TitleMarginLeft, 0, 0)
	propertyLabel.Parent = propertyLabelFrame

	local propertyValueFrame = CreateCell()
	propertyValueFrame.Size = UDim2.new(0.5, -1, 1, 0)
	propertyValueFrame.Position = UDim2.new(0.5, 0, 0, 0)
	propertyValueFrame.Parent = rowFrame

	local control = GetControl(object, propertyData, readOnly)
	control.Parent = propertyValueFrame

	rowFrame.MouseEnter:connect(function()
		propertyLabelFrame.BackgroundColor3 = Row.BackgroundColorMouseover
		propertyValueFrame.BackgroundColor3 = Row.BackgroundColorMouseover
	end)
	rowFrame.MouseLeave:connect(function()
		propertyLabelFrame.BackgroundColor3 = backColor
		propertyValueFrame.BackgroundColor3 = backColor
	end)

	propertyLabelFrame.BackgroundColor3 = backColor
	propertyValueFrame.BackgroundColor3 = backColor

	return rowFrame
end

function ClearPropertiesList()
	for _,instance in pairs(ContentFrame:GetChildren()) do
		instance:Destroy()
	end
end

local selection = Gui:FindFirstChild("Selection", 1)

function displayProperties(props)
	for i,v in pairs(props) do
		pcall(function()
			local a = CreateRow(v.object, v.propertyData, ((numRows % 2) == 0))
			a.Position = UDim2.new(0,0,0,numRows*Row.Height)
			a.Parent = ContentFrame
			numRows = numRows + 1
		end)
	end
end

function checkForDupe(prop,props)
	for i,v in pairs(props) do
		if v.propertyData.Name == prop.Name and v.propertyData.ValueType.Category == prop.ValueType.Category and v.propertyData.ValueType.Name == prop.ValueType.Name then
			return true
		end
	end
	return false
end

function sortProps(t)
	table.sort(t,
		function(x,y) return x.propertyData.Name < y.propertyData.Name
	end)
end

function showProperties(obj)
	ClearPropertiesList()
	if obj == nil then return end
	local propHolder = {}
	local foundProps = {}
	numRows = 0
	for _,nextObj in pairs(obj) do
		if not foundProps[nextObj.className] then
			foundProps[nextObj.className] = true
			for i,v in pairs(RbxApi.GetProperties(nextObj.className)) do
				local suc, err = pcall(function()
					if not (PropertyIsHidden(v)) and not checkForDupe(v,propHolder) then
						if string.find(string.lower(v.Name),string.lower(propertiesSearch.Text)) or not searchingProperties() then
							table.insert(propHolder,{propertyData = v, object = nextObj})
						end
					end
				end)
				--[[if not suc then
					warn("Problem getting the value of property " .. v.Name .. " | " .. err)
				end	--]]
			end
		end
	end
	sortProps(propHolder)
	displayProperties(propHolder)
	ContentFrame.Size = UDim2.new(1, 0, 0, numRows * Row.Height)
	scrollBar.ScrollIndex = 0
	scrollBar.TotalSpace = numRows * Row.Height
	scrollBar.Update()
end
