Advertisement
nonogamer9

test

Aug 26th, 2024 (edited)
33
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 9.56 KB | None | 0 0
  1. local component = require("component")
  2. local event = require("event")
  3. local internet = require("internet")
  4. local term = require("term")
  5. local unicode = require("unicode")
  6. local gpu = component.gpu
  7.  
  8. local hasColor = gpu.getDepth() > 1
  9.  
  10. local function bootUpScreen()
  11. term.clear()
  12. local logo = [[
  13. :::::::: :::::::: ::: ::: :::::::::: :::::::::
  14. :+: :+: :+: :+: :+: :+: :+: :+:
  15. +:+ +:+ +:+ +:+ +:+ +:+ +:+ +:+
  16. +#+ +:+ +#++:++#++: +#++:++#++ +#++:++#+
  17. +#+ +#+ +#+ +#+ +#+ +#+
  18. #+# #+# #+# #+# #+# #+#
  19. ######## ### ### ### ###
  20. ]]
  21. term.setCursor(1, 1)
  22. term.write(logo)
  23. term.setCursor(1, select(2, term.getCursor()) + 1)
  24. term.write("Loading...")
  25. term.setCursor(1, select(2, term.getCursor()) + 2)
  26. term.write("OC-WEB: A Web Browser For OpenComputers Coded by nonogamer9")
  27. os.sleep(3)
  28. end
  29.  
  30. local function resolveURL(base, relative)
  31. if not base or not relative then return nil end
  32. if relative:match("^https?://") then return relative end
  33. if relative:sub(1, 1) == "/" then
  34. return base:match("^(https?://[^/]+)") .. relative
  35. else
  36. local baseMatch = base:match("^(https?://.*/)") or base:match("^(https?://[^/]+)")
  37. if baseMatch then
  38. if baseMatch:sub(-1) ~= "/" then
  39. baseMatch = baseMatch .. "/"
  40. end
  41. return baseMatch .. relative
  42. else
  43. return nil
  44. end
  45. end
  46. end
  47.  
  48. local function handleJavaScript(html, currentBaseURL)
  49. local redirectUrl = html:match("window%.location%s*=%s*['\"](.-)['\"]")
  50. if redirectUrl then
  51. return resolveURL(currentBaseURL, redirectUrl)
  52. end
  53. return nil
  54. end
  55.  
  56. local function fetch(url, visited)
  57. visited = visited or {}
  58. if visited[url] then
  59. return false, "Redirect loop detected"
  60. end
  61. visited[url] = true
  62.  
  63. local handle, err = internet.request(url)
  64. if not handle then
  65. return false, "Failed to connect to " .. url .. ": " .. (err or "unknown error")
  66. end
  67.  
  68. local data = ""
  69. for chunk in handle do
  70. if chunk then
  71. data = data .. chunk
  72. end
  73. end
  74.  
  75. local redirectUrl = handleJavaScript(data, url)
  76. if redirectUrl then
  77. return fetch(redirectUrl, visited)
  78. end
  79.  
  80. return true, data
  81. end
  82.  
  83. local function parseCSS(css)
  84. local styles = {}
  85. for selector, rules in css:gmatch("([^{]+){([^}]+)}") do
  86. styles[selector:gsub("%s+", "")] = {}
  87. for property, value in rules:gmatch("([^:]+):([^;]+);") do
  88. styles[selector:gsub("%s+", "")][property:gsub("%s+", "")] = value:gsub("%s+", "")
  89. end
  90. end
  91. return styles
  92. end
  93.  
  94. local function applyCSS(html, styles)
  95. for selector, rules in pairs(styles) do
  96. local pattern = "<" .. selector .. ">(.-)</" .. selector .. ">"
  97. html = html:gsub(pattern, function(content)
  98. local styled = content
  99. for property, value in pairs(rules) do
  100. if property == "color" then
  101. styled = "[COLOR=" .. value .. "]" .. styled .. "[/COLOR]"
  102. end
  103. -- Add more property handlers here as needed
  104. end
  105. return styled
  106. end)
  107. end
  108. return html
  109. end
  110.  
  111. local function executeJavaScript(script)
  112. -- This is a placeholder. Implementing a full JS engine is beyond the scope of this project.
  113. print("Executing JavaScript:", script:sub(1, 50) .. "...")
  114. end
  115.  
  116. local function parseHTML(html, baseURL)
  117. local links = {}
  118. local styles = {}
  119.  
  120. -- Extract and parse CSS
  121. html = html:gsub("<style>(.-)</style>", function(css)
  122. local parsedStyles = parseCSS(css)
  123. for k, v in pairs(parsedStyles) do
  124. styles[k] = v
  125. end
  126. return ""
  127. end)
  128.  
  129. -- Extract and execute JavaScript
  130. html = html:gsub("<script>(.-)</script>", function(js)
  131. executeJavaScript(js)
  132. return ""
  133. end)
  134.  
  135. -- Parse HTML elements
  136. html = html:gsub("<b>(.-)</b>", function(content) return "[B]" .. content .. "[/B]" end)
  137. html = html:gsub("<strong>(.-)</strong>", function(content) return "[B]" .. content .. "[/B]" end)
  138. html = html:gsub("<i>(.-)</i>", function(content) return "[I]" .. content .. "[/I]" end)
  139. html = html:gsub("<em>(.-)</em>", function(content) return "[I]" .. content .. "[/I]" end)
  140. html = html:gsub("<u>(.-)</u>", function(content) return "[U]" .. content .. "[/U]" end)
  141. html = html:gsub('<a href="(.-)">(.-)</a>', function(href, content)
  142. local fullURL = resolveURL(baseURL, href)
  143. table.insert(links, {href = fullURL, content = content})
  144. return content .. " [" .. #links .. "]"
  145. end)
  146. html = html:gsub("<h[1-6]>(.-)</h[1-6]>", function(content) return "[H]" .. content .. "[/H]" end)
  147. html = html:gsub("<li>(.-)</li>", function(content) return " * " .. content end)
  148. html = html:gsub("<br>", "\n")
  149. html = html:gsub("<p>", "\n\n")
  150. html = html:gsub("</p>", "\n\n")
  151. html = html:gsub("<div>(.-)</div>", function(content) return content .. "\n" end)
  152. html = html:gsub("<.->", "")
  153. html = html:gsub("&lt;", "<")
  154. html = html:gsub("&gt;", ">")
  155. html = html:gsub("&amp;", "&")
  156. html = html:gsub("&quot;", "\"")
  157. html = html:gsub("&apos;", "'")
  158.  
  159. -- Apply CSS
  160. html = applyCSS(html, styles)
  161.  
  162. return html, links
  163. end
  164.  
  165. local function display(baseURL, data, links)
  166. local lines = {}
  167. for line in data:gmatch("[^\r\n]+") do
  168. table.insert(lines, line)
  169. end
  170.  
  171. local offset = 0
  172. local screenWidth, screenHeight = gpu.getResolution()
  173. local contentHeight = screenHeight - 1
  174.  
  175. local function redraw()
  176. term.setCursor(1, 1)
  177. for i = 1, contentHeight do
  178. local line = lines[i + offset] or ""
  179. term.setCursor(1, i)
  180. term.clearLine()
  181. -- Handle color tags
  182. line = line:gsub("%[COLOR=(%w+)%](.-)%[/COLOR%]", function(color, text)
  183. if hasColor then
  184. gpu.setForeground(tonumber(color, 16) or 0xFFFFFF)
  185. end
  186. return text
  187. end)
  188. term.write(unicode.sub(line, 1, screenWidth))
  189. if hasColor then
  190. gpu.setForeground(0xFFFFFF) -- Reset color
  191. end
  192. end
  193. term.setCursor(1, screenHeight)
  194. gpu.setBackground(0x333333)
  195. term.clearLine()
  196. term.write("URL: " .. (baseURL or "N/A") .. " | Use Arrow Keys to Scroll, Q to Quit, U to Change URL")
  197. gpu.setBackground(0x000000)
  198. end
  199.  
  200. redraw()
  201.  
  202. while true do
  203. local eventType, _, _, y, _, scrollDirection = event.pull()
  204. local needsRedraw = false
  205.  
  206. if eventType == "key_down" then
  207. if y == 200 then -- Up arrow
  208. offset = math.max(0, offset - 1)
  209. needsRedraw = true
  210. elseif y == 208 then -- Down arrow
  211. offset = math.min(#lines - contentHeight, offset + 1)
  212. needsRedraw = true
  213. elseif y
  214.  
  215. == 16 then -- Q key
  216. break
  217. elseif y == 22 then -- U key
  218. return false
  219. end
  220. elseif eventType == "scroll" then
  221. if scrollDirection == 1 then
  222. offset = math.max(0, offset - 1)
  223. needsRedraw = true
  224. elseif scrollDirection == -1 then
  225. offset = math.min(#lines - contentHeight, offset + 1)
  226. needsRedraw = true
  227. end
  228. elseif eventType == "touch" then
  229. local lineIndex = y + offset
  230. if lineIndex <= #lines then
  231. local line = lines[lineIndex]
  232. local linkIndex = line:match("%[(%d+)%]$")
  233. if linkIndex then
  234. local link = links[tonumber(linkIndex)]
  235. if link and link.href then
  236. local resolvedURL = resolveURL(baseURL, link.href)
  237. if resolvedURL then
  238. print("Opening link: " .. resolvedURL)
  239. local success, newData = fetch(resolvedURL)
  240. if success then
  241. local newParsedData, newLinks = parseHTML(newData, resolvedURL)
  242. display(resolvedURL, newParsedData, newLinks)
  243. else
  244. print("Error fetching URL: " .. newData)
  245. end
  246. else
  247. print("Invalid URL: " .. tostring(link.href))
  248. end
  249. else
  250. print("Invalid link at index: " .. linkIndex)
  251. end
  252. end
  253. end
  254. end
  255.  
  256. if needsRedraw then
  257. redraw()
  258. end
  259. end
  260. end
  261.  
  262. function main(showBootScreen)
  263. if showBootScreen then
  264. bootUpScreen()
  265. end
  266.  
  267. term.clear()
  268. print("Enter a URL:")
  269. local url = io.read()
  270.  
  271. if not url:match("^https?://") then
  272. print("Invalid URL. Please include http:// or https://")
  273. else
  274. local success, data = fetch(url)
  275. if success then
  276. local parsedData, links = parseHTML(data, url)
  277. if display(url, parsedData, links) == false then
  278. main(false)
  279. end
  280. else
  281. print("Error fetching URL: " .. data)
  282. end
  283. end
  284. end
  285.  
  286. main(true)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement