Lots of changes

Images can now be shown. They are also shown on index.
The framework for boosting, favoriting, and replying have been layed out.
Bug fixes and a small rework to make things easier.
This commit is contained in:
CatAClock 2025-05-10 19:36:57 -07:00
parent 8b66616c4e
commit cda2765df1
6 changed files with 164 additions and 32 deletions

View file

@ -13,10 +13,16 @@
<body style="margin: 0px; text-align: center;">
<header>
<h1 class="Handle"></h1>
<h2 class="Origin">Bsky/Mastodon (TODO)</h2>
<p class="DetailedText"></p>
<p>Image here if it is a thing (TODO)</p>
<p onclick="history.back()"><b>Back</b></p>
<h2 class="Origin"></h2>
</header>
<p class="PostText"></p>
<div class="Images">
</div>
<div>
<p class="Favorite">Favorite!</p>
<p class="Boost">Boost!</p>
<p class="Reply">Reply!</p>
</div>
<p onclick="history.back()"><b>Back</b></p>
</body>
</html>

View file

@ -26,6 +26,33 @@ export async function GetTimeline(Cursor) {
return body;
}
export async function GetPosts(URIs) {
if (localStorage.getItem(Variables.BlueskyAccessToken) == null) {
console.log("No access token!");
return "";
}
let PDS = localStorage.getItem(Variables.BlueskyPDS);
let DPoP = await ClientDPoPPDS("GET", PDS + "/xrpc/app.bsky.feed.getPosts?uris=" + URIs);
let request = fetch(PDS + "/xrpc/app.bsky.feed.getPosts?uris=" + URIs, { method: "GET", headers: {"Authorization": "DPoP " + localStorage.getItem(Variables.BlueskyAccessToken), "DPoP": DPoP}});
let body = await request.then((response) => response.json());
let status = await request.then((response) => response.status);
let header = await request.then((response) => response.headers.get("dpop-nonce"));
if (status == 401) {
await HandleError(body, header);
body = await GetPosts(URIs);
}
return body;
}
// Get a blob (like an image or video). Authentication need not apply.
export async function GetBlob(DID, CID) {
let PDS = localStorage.getItem(Variables.BlueskyPDS);
let request = fetch("https://bsky.social/xrpc/com.atproto.sync.getBlob?did=" + DID + "&cid=" + CID, {method: "GET"});
let body = await request.then((response) => response.json());
return body;
}
export async function CreatePost(DID, Text) {
if (localStorage.getItem(Variables.BlueskyAccessToken) == null) {
console.log("No access token!");

View file

@ -77,6 +77,17 @@ export async function GetNotifications() {
.then((response) => response.json());
}
export async function GetStatus(ID) {
if (localStorage.getItem(Variables.MastodonAccessToken) == null) {
console.log("No access token!");
return "";
}
let Website = localStorage.getItem(Variables.MastodonWebsite);
// Get the varaibles that are stored in Variables and then input it.
return await fetch(Website + "/api/v1/statuses/" + ID, {method: "GET", headers: {"Authorization": localStorage.getItem(Variables.MastodonTokenType) + " " + localStorage.getItem(Variables.MastodonAccessToken)}})
.then((response) => response.json());
}
// Make a status
export async function CreateStatus(Text, Visibility = "public") {
if (localStorage.getItem(Variables.MastodonAccessToken) == null) {

View file

@ -1,5 +1,56 @@
let content = decodeURI(document.location.href.split("content=")[1]);
let username = decodeURI(document.location.href.split("username=")[1].split("&content")[0]);
import * as MastodonAPI from "./MastodonAPI.js";
import * as BlueskyAPI from "./BlueskyAPI.js";
import * as TumblrAPI from "./TumblrAPI.js";
import * as Variables from "./Variables.js";
document.getElementsByClassName("Handle")[0].innerHTML = username;
document.getElementsByClassName("DetailedText")[0].innerHTML = content;
// Buttons
let Favorite = document.getElementsByClassName("Favorite")[0];
let Boost = document.getElementsByClassName("Boost")[0];
let Reply = document.getElementsByClassName("Reply")[0];
// Variables
let website = document.location.href.split("website=")[1];
let post = JSON.parse(localStorage.getItem("post"));
document.getElementsByClassName("Origin")[0].innerHTML = website;
GetPost();
// Button stuff
// Functions and things.
async function GetPost() {
console.log(post);
if (website == "Mastodon") {
// Check for a reblog.
if (post.reblog != null) {
document.getElementsByClassName("PostText")[0].innerHTML = post.reblog.content;
document.getElementsByClassName("Handle")[0].innerHTML = post.reblog.account.username + " ( R: " + post.account.username + " )";
} else {
document.getElementsByClassName("PostText")[0].innerHTML = post.content;
document.getElementsByClassName("Handle")[0].innerHTML = post.account.username;
}
// Show the image if it exists.
if (post.media_attachments.length != 0) {
for (let i of post.media_attachments) {
document.getElementsByClassName("Images")[0].innerHTML = document.getElementsByClassName("Images")[0].innerHTML + "<img src=" + i.remote_url + " alt='" + i.description + "'/>";
}
}
} else if (website == "Bluesky") {
// Check for a reblog.
if (post.hasOwnProperty("reason") && post.reason.$type == "app.bsky.feed.defs#reasonRepost") {
document.getElementsByClassName("PostText")[0].innerHTML = post.post.record.text;
document.getElementsByClassName("Handle")[0].innerHTML = post.post.author.handle + " ( R: " + post.reason.by.handle + " )";
} else {
document.getElementsByClassName("PostText")[0].innerHTML = post.post.record.text;
document.getElementsByClassName("Handle")[0].innerHTML = post.post.author.handle;
}
// Show the image if it exists.
if (post.post.record.hasOwnProperty("embed") && post.post.record.embed.$type == "app.bsky.embed.images") {
for (let i of post.post.embed.images) {
document.getElementsByClassName("Images")[0].innerHTML = document.getElementsByClassName("Images")[0].innerHTML + "<img src=" + i.fullsize + " alt='" + i.alt + "'/>";
}
}
} else {
document.getElementsByClassName("PostText")[0].innerHTML = "Nothing to load.";
}
}

View file

@ -101,27 +101,45 @@ ArrowsButton[0].onclick = (event) => {
}
}
for (let i of ClickableContainers) {
i.onclick = (event) => {
let content = i.getElementsByClassName("PostContent")[0].innerHTML
let username = i.getElementsByClassName("Username")[0].innerHTML
// Save some info
window.location.href = "./HTML/expanded.html?username=" + username + "&content=" + content;
}
}
// These numbers are here so you don't go back.
let MastodonLoadedFeed = [];
let BlueskyLoadedFeed = [];
let CurrentThing = 0;
let WebsiteAPIType = [];
let Mastodon = true;
let Bluesky = true;
// This will allow you to click on a post and get an "expended" version of that post.
for (let i of ClickableContainers) {
i.onclick = (event) => {
let number = parseInt(i.getAttribute("number"));
let post;
let website;
// Roundabout way of doing things. Very funny.
website = WebsiteAPIType[number];
if (WebsiteAPIType[number] == "Mastodon") {
post = MastodonLoadedFeed[CurrentThing + number];
} else if (WebsiteAPIType[number] == "Bluesky") {
if (Mastodon == true) {
// *hardcoded bullshit*
number = number - 6;
}
post = BlueskyLoadedFeed[CurrentThing + number];
} else {
return;
}
// Save some info
localStorage.setItem("post", JSON.stringify(post));
document.location.href = "./HTML/expanded.html?website=" + website;
}
}
// Call this to update the things :)
async function PosterContainerUpdate(Direction) {
let Lim = 6;
let Website = localStorage.getItem(Variables.MastodonWebsite);
let Mastodon = true;
// Mastodon gaining of timeline.
if (localStorage.getItem(Variables.MastodonWebsite) == null) {
// The default website is Wetdry :3
@ -135,6 +153,7 @@ async function PosterContainerUpdate(Direction) {
if (localStorage.getItem(Variables.BlueskyPDS) == null) {
console.log("No Bluesky instance. multiplying mastodon posts by 2...");
Lim = Lim * 2;
Bluesky = false;
} else if (BlueskyLoadedFeed.length == 0) {
BlueskyLoadedFeed = await BlueskyAPI.GetTimeline("").then((response) => response.feed);
}
@ -155,12 +174,17 @@ async function PosterContainerUpdate(Direction) {
if (Mastodon == false) {
countergroup = countergroup + 1;
}
if (Bluesky == false) {
countergroup = countergroup + 1;
}
// This var is meant to stop "already seen" posts.
let BlueskyPostsDup = [];
WebsiteAPIType = [];
for (let i of ClickableContainers) {
switch(countergroup) {
// Mastodon
case 0:
WebsiteAPIType.push("Mastodon");
if (MastodonLoadedFeed[CurrentThing + counter] == undefined) {
let TempFeed = await MastodonAPI.GetTimeline(MastodonLoadedFeed[CurrentThing + counter - 1].id);
MastodonLoadedFeed = MastodonLoadedFeed.concat(TempFeed);
@ -179,9 +203,14 @@ async function PosterContainerUpdate(Direction) {
i.getElementsByClassName("PostContent")[0].innerHTML = MastodonLoadedFeed[CurrentThing + counter].content;
i.getElementsByClassName("Username")[0].innerHTML = MastodonLoadedFeed[CurrentThing + counter].account.username;
}
// Check for images.
if (MastodonLoadedFeed[CurrentThing + counter].media_attachments.length != 0) {
i.getElementsByClassName("PostContent")[0].innerHTML = i.getElementsByClassName("PostContent")[0].innerHTML + "<br/>This post has an image!";
}
break;
// Bsky
case 1:
WebsiteAPIType.push("Bluesky");
if (BlueskyLoadedFeed[CurrentThing + counter] == undefined) {
let TempFeed = await BlueskyAPI.GetTimeline(BlueskyLoadedFeed[CurrentThing + counter - 1].post.indexedAt).then((response) => response.feed)
BlueskyLoadedFeed = BlueskyLoadedFeed.concat(TempFeed);
@ -207,7 +236,14 @@ async function PosterContainerUpdate(Direction) {
i.getElementsByClassName("PostContent")[0].innerHTML = BlueskyLoadedFeed[CurrentThing + counter].post.record.text;
i.getElementsByClassName("Username")[0].innerHTML = BlueskyLoadedFeed[CurrentThing + counter].post.author.handle;
}
// Direction for where you go :3
// Check for an image
if (BlueskyLoadedFeed[CurrentThing + counter].post.record.hasOwnProperty("embed") && BlueskyLoadedFeed[CurrentThing + counter].post.record.embed.$type == "app.bsky.embed.images") {
i.getElementsByClassName("PostContent")[0].innerHTML = i.getElementsByClassName("PostContent")[0].innerHTML + "<br/><br/>This post has an image!";
}
break;
case 2:
WebsiteAPIType.push("Nothing");
console.log("The number you are trying to reach is unavailable. Try signing in dumbass.");
break;
}
counter = counter + 1;
@ -216,6 +252,7 @@ async function PosterContainerUpdate(Direction) {
countergroup = countergroup + 1;
}
}
console.log(WebsiteAPIType);
}
// Assistant function to help with checking for duplicates.

View file

@ -135,51 +135,51 @@
<!-- This is the container that houses the current viewing stuff -->
<div class="PostContainer">
<article class="Post">
<article number=0 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=1 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=2 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=3 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=4 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=5 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=6 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=7 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=8 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=9 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=10 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>
<article class="Post">
<article number=11 class="Post">
<p class="Username"></p>
<p class="PostContent"></p>
</article>