Last active
March 20, 2023 14:45
-
-
Save kyubuns/4fce95c0bc94032c3d5b7661be137a0f to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!DOCTYPE html> | |
<html lang="ja"> | |
<head> | |
<meta charset="UTF-8"> | |
<meta name="viewport" content="width=device-width, initial-scale=1.0"> | |
<title>ChatGPT Twitter-like Webpage</title> | |
<style> | |
body { | |
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol'; | |
background-color: #f5f8fa; | |
color: #14171a; | |
margin: 0; | |
padding: 0; | |
} | |
.container { | |
max-width: 600px; | |
margin: 50px auto; | |
padding: 20px; | |
background-color: #fff; | |
border-radius: 10px; | |
box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1), 0 1px 3px rgba(0, 0, 0, 0.08); | |
} | |
h1 { | |
font-size: 28px; | |
font-weight: bold; | |
text-align: center; | |
margin-bottom: 20px; | |
} | |
.tweet { | |
display: flex; | |
flex-direction: column; | |
margin-bottom: 20px; | |
} | |
.input { | |
font-size: 16px; | |
border: 1px solid #ccd6dd; | |
border-radius: 5px; | |
padding: 10px; | |
resize: none; | |
outline: none; | |
} | |
button { | |
font-size: 16px; | |
font-weight: bold; | |
color: #fff; | |
background-color: #1da1f2; | |
padding: 10px 16px; | |
border: none; | |
border-radius: 25px; | |
cursor: pointer; | |
outline: none; | |
margin-top: 10px; | |
transition: background-color 0.2s; | |
} | |
button:hover { | |
background-color: #0c85d0; | |
} | |
.conversation { | |
margin-bottom: 20px; | |
padding: 15px; | |
background-color: #f5f8fa; | |
border-radius: 5px; | |
} | |
.message { | |
font-size: 16px; | |
padding: 10px; | |
border-radius: 5px; | |
} | |
.tweet-message { | |
background-color: #e8f5fe; | |
color: #1c1e21; | |
margin-bottom: 10px; | |
} | |
.reply-message { | |
background-color: #eff9ff; | |
color: #1c1e21; | |
} | |
.avatar { | |
width: 48px; | |
height: 48px; | |
border-radius: 50%; | |
object-fit: cover; | |
margin-right: 10px; | |
} | |
.user-info { | |
display: flex; | |
flex-direction: column; | |
align-items: center; | |
margin-bottom: 5px; | |
} | |
.message-container { | |
display: flex; | |
} | |
</style> | |
<script> | |
async function sendTweet() { | |
const tweet = document.getElementById('tweet-input').value; | |
document.getElementById('tweet-input').value = ''; | |
const conversation = displayTweet(tweet); | |
const numReplies = Math.floor(Math.random() * 3) + 1; | |
const replies = await fetchReplies(tweet, numReplies); | |
let delay = 0; | |
for (let reply of replies) { | |
setTimeout(() => { | |
displayReply(reply, conversation); | |
}, delay); | |
delay += Math.floor(Math.random() * 2000) + 2000; | |
} | |
} | |
async function fetchReplies(tweet, numReplies) { | |
const apiKey = 'YOUR_API_KEY_HERE'; | |
const url = 'https://api.openai.com/v1/chat/completions'; | |
const messages = [ | |
{"role": "user", "content": `ここはツイッターです。次のツイートに気の利いたリプライを返してください。明るい気持ちになるような、優しい発言や、面白い発言のみを使ってください。: "${tweet}"`} | |
] | |
const body = JSON.stringify({ | |
"model": "gpt-3.5-turbo", | |
"messages": messages, | |
"n": numReplies | |
}) | |
const response = await fetch(url, { | |
method: 'POST', | |
headers: { | |
'Content-Type': 'application/json', | |
'Authorization': `Bearer ${apiKey}`, | |
}, | |
body: body, | |
}); | |
const data = await response.json(); | |
console.log(data) | |
return data.choices.map(choice => choice.message.content.trim()); | |
} | |
function displayTweet(tweet) { | |
const conversation = document.createElement('div'); | |
conversation.className = 'conversation'; | |
const messageContainer = document.createElement('div'); | |
messageContainer.className = 'message-container'; | |
const avatar = document.createElement('img'); | |
avatar.src = 'https://kyubuns.dev/icons/1024_full.png'; // 適当なアイコン | |
avatar.className = 'avatar'; | |
const message = document.createElement('div'); | |
message.className = 'message tweet-message'; | |
const userInfo = document.createElement('div'); | |
userInfo.className = 'user-info'; | |
userInfo.textContent = '名前'; | |
message.textContent = tweet; | |
userInfo.appendChild(avatar); | |
messageContainer.appendChild(userInfo); | |
messageContainer.appendChild(message); | |
conversation.appendChild(messageContainer); | |
document.getElementById('conversations').prepend(conversation); | |
return conversation; | |
} | |
function displayReply(reply, conversation) { | |
reply = reply.replace(/["<>]/g, ''); // カギカッコとダブルクオートを削除 | |
const messageContainer = document.createElement('div'); | |
messageContainer.className = 'message-container'; | |
const avatar = document.createElement('img'); | |
avatar.src = generateRandomAvatarUrl(); | |
avatar.className = 'avatar'; | |
const message = document.createElement('div'); | |
message.className = 'message reply-message'; | |
const userInfo = document.createElement('div'); | |
userInfo.className = 'user-info'; | |
userInfo.textContent = generateRandomJapaneseName(); | |
message.textContent = reply; | |
userInfo.appendChild(avatar); | |
messageContainer.appendChild(userInfo); | |
messageContainer.appendChild(message); | |
conversation.appendChild(messageContainer); | |
} | |
function generateRandomJapaneseName() { | |
const nicknames = ['さとぴー', 'すずきん', 'たかはしくん', 'たなかたろう', 'いとぅい', 'わたなべゆう', 'やまもとけい', 'なかむらりん', 'こばやしちゃん', 'かとうこ']; | |
return nicknames[Math.floor(Math.random() * nicknames.length)]; | |
} | |
function generateRandomAvatarUrl() { | |
const avatarIds = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]; | |
return `https://randomuser.me/api/portraits/thumb/men/${avatarIds[Math.floor(Math.random() * avatarIds.length)]}.jpg`; | |
} | |
document.addEventListener('DOMContentLoaded', () => { | |
document.getElementById('tweet-input').addEventListener('keydown', (event) => { | |
const isCmdOrCtrl = event.metaKey || event.ctrlKey; | |
if (isCmdOrCtrl && event.key === 'Enter') { | |
sendTweet(); | |
} | |
}); | |
}); | |
</script> | |
</head> | |
<body> | |
<div class="container"> | |
<h1>Twitter-like ChatGPT Webpage</h1> | |
<div class="tweet"> | |
<textarea id="tweet-input" class="input" rows="3" placeholder="Write your tweet here..."></textarea> | |
<button onclick="sendTweet()">Tweet</button> | |
</div> | |
<div id="conversations"> | |
<!-- Conversations will be displayed here --> | |
</div> | |
</div> | |
</body> | |
</html> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment