import { div, pfp, banner, parse, button, body, a, span, crawl, parseDate, parseMonth } from './main.js' import { loadself, loadusers, loadusersposts, updateavatar, updatebanner, logout, follow, follow_status, friends } from './api.js' import { parsePost, parseUser, header } from './components.js' function swap(tab) { let buttons = [] buttons[0] = document.querySelector("#profilepostbutton"); buttons[1] = document.querySelector("#profileaboutbutton"); buttons[2] = document.querySelector("#profilefriendsbutton"); buttons[3] = document.querySelector("#profilefollowersbutton"); buttons[4] = document.querySelector("#profilefollowingbutton"); let sections = [] sections[0] = document.querySelector("#posts"); sections[1] = document.querySelector("#about"); sections[2] = document.querySelector("#friends"); sections[3] = document.querySelector("#followers"); sections[4] = document.querySelector("#following"); let load = document.querySelector(".loadp"); for (const i in buttons) { if (i == tab) { buttons[i].classList.add("selected") sections[i].classList.remove("hidden") } else { buttons[i].classList.remove("selected") sections[i].classList.add("hidden") } } if (load) { if (tab == 0) { load.classList.remove("hidden") } else { load.classList.add("hidden") } } } function changeimage(fn) { var input = document.createElement('input') input.type = 'file' input.accept= 'image/png' input.onchange = async (e) => { var popup = document.getElementById("popup") var loader = popup.getElementsByClassName("loading")[0] var message = popup.getElementsByClassName("message")[0] loader.classList.add("hidden") message.innerHTML = ''; popup.classList.remove("hidden") var file = e.target.files[0]; if (file.type !== 'image/png') { message.innerHTML = 'Image must be a PNG'; return } loader.classList.remove("hidden") let response = await fn(file); loader.classList.add("hidden") message.innerHTML = response.msg } input.click(); } function status_text(status) { switch (status) { case 1: return 'Following ✓' case 2: return 'Follow Back' case 3: return 'Friends ✓' default: return 'Follow' } } async function render() { let status; if (!isself) { let response = await follow_status(data.user.user_id) if (response.status == 200) { status = parseInt(response.msg) } else { status = 0; } } let response = (await friends(data.user.user_id)).json if (response == undefined) { response = [] } let friends_arr = response[0]; let followers = response[1]; let following = response[2]; let new_body = body({}, ...header(false, false, false, data.self.user_id), div({id: 'top'}, div({id: 'banner'}, div({class: 'bg'}, banner(data.user.user_id) ), isself ? div({class: 'changebanner', onclick: () => changeimage(updatebanner)}) : parse(''), ), div({id: 'info'}, div({class: 'face'}, pfp(data.user.user_id), isself ? div({class: 'changeavatar', onclick: () => changeimage(updateavatar)}) : parse(''), ), div({class: 'infodata'}, span({class: 'bold ltext'}, parse(data.user.firstname + ' ' + data.user.lastname) ), span({class: 'gtext'}, parse('Joined ' + parseDate(new Date(data.user.date))) ) ), !isself ? div({class: 'right'}, div({class: `follow ${status == 3 ? 'friend' : ''}`, onclick: async (event) => { let button = event.target if (button.tagName == 'SPAN') { button = button.parentElement } let response if (status % 2 == 0) { response = await follow(true, data.user.user_id); } else { response = await follow(false, data.user.user_id); } if (response.status == 200) { status = parseInt(response.msg) } else { return } button.firstChild.innerHTML = status_text(status) if (status == 3) { button.classList.add('friend') } else { button.classList.remove('friend') } }}, span({class: 'gtext'}, parse(status_text(status)) ) ) ) : parse('') ), div({class: 'fullline', style: 'width: 80em; margin-bottom: 0; z-index: 0;'}), div({class: 'profilebuttons'}, button({id: 'profilepostbutton', class: 'selected', onclick: () => swap(0)}, parse('Posts') ), button({id: 'profileaboutbutton', onclick: () => swap(1)}, parse('About') ), button({id: 'profilefriendsbutton', onclick: () => swap(2)}, parse('Friends') ), button({id: 'profilefollowersbutton', onclick: () => swap(3)}, parse('Followers') ), button({id: 'profilefollowingbutton', onclick: () => swap(4)}, parse('Following') ), div({style: 'flex: 20'}), isself ? button({class: 'logout', onclick: async () => { const response = await logout() if (response.status != 200) return; location.href = '/login' }}, parse('Logout') ) : parse('') ) ), div({id: 'posts'}, ...data.posts.map(p => parsePost(p, data.users, data.self)) ), div({id: 'load'}, a({class: 'loadp bold gtext', onclick: async () => { const posts = await load() data.posts.push(... posts) const el = document.getElementById("posts") for (const post of posts) { el.appendChild( parsePost(post, data.users, data.self) ) } }}, parse('Load more posts') ) ), div({id: 'about', class: 'post hidden'}, span({class: 'bold ltext'}, parse('About') ), div({class: 'data'}, span({class: 'gtext bold'}, parse('Name: ' + data.user.firstname + ' ' + data.user.lastname) ), span({class: 'gtext bold'}, parse('Email: ' + data.user.email) ), span({class: 'gtext bold'}, parse('Gender: ' + data.user.gender) ), span({class: 'gtext bold'}, parse('Birthday: ' + parseMonth(data.user.month) + ' ' + data.user.day + ', ' + data.user.year) ), span({class: 'gtext bold'}, parse('User ID: ' + data.user.user_id) ) ) ), div({id: 'friends', class: 'hidden'}, ...friends_arr.map(u => parseUser(u)) ), div({id: 'followers', class: 'hidden'}, ...followers.map(u => parseUser(u)) ), div({id: 'following', class: 'hidden'}, ...following.map(u => parseUser(u)) ), div({id: 'popup', class: 'hidden'}, div({class: 'createpost'}, div({class: 'close', onclick: () => document.getElementById('popup').classList.add('hidden')}), span({class: 'ltext ctext bold'}, parse('Uploading') ), div({class: 'fullline'}), div({class: 'fullwidth'}, div({class: 'loading'}, div({}), div({}), div({}), div({}) ) ), span({class: 'message ctext', style: 'padding-top: 10px'}) ) ) ) document.body.replaceWith(new_body) if (data.posts.length < 10) { document.getElementById('load').remove() } } var isself = false var page = 0 const data = { self: {}, user: {}, users: {}, posts: [] } async function load(id) { if (id === undefined) { id = data.user.user_id } const posts = (await loadusersposts(id, page)).json if (posts == undefined) { posts = [] } if (posts.length < 1) { let el = document.getElementsByClassName('loadp')[0] if (el) { el.remove() } } else { page++ } const batch = Array.from(new Set(crawl('user_id', posts))).filter(id => data.users[id] == undefined) if (!isself) { batch.push(id) } if (batch.length != 0) { const users = (await loadusers(batch)).json if (users == undefined) { users = [] } for (const user of users) { data.users[user.user_id] = user } } return posts } async function init() { let request = await loadself() if (request.status === 429) { let new_body = body({}, ...header(false, false) ) document.body.replaceWith(new_body) throw new Error("Rate limited"); } if (request.json == undefined) { location.href = '/login' return } data.self = request.json; data.users[data.self.user_id] = data.self var params = {}; for (const [key, value] of new URLSearchParams(location.search)) { params[key] = value } let id; if (params.id !== undefined && !isNaN(params.id)) { id = parseInt(params.id); } else { id = data.self.user_id } isself = id === data.self.user_id const posts = await load(id) data.posts.push(... posts) data.user = data.users[id] render() } init()