forked from zero-to-mastery/ZTM-Quest
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathmailboxMainArea.interaction.js
More file actions
141 lines (124 loc) · 3.91 KB
/
Copy pathmailboxMainArea.interaction.js
File metadata and controls
141 lines (124 loc) · 3.91 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
import { time } from '../../kplayCtx';
import { displayDialogue, showCustomPrompt } from '../../utils';
import { fetchNews, formatNewsDate } from '../../utils/newsApi';
// Cache for news to avoid fetching multiple times
let newsCache = null;
let abort;
/**
* Show detailed view of a specific news article with back button
*/
const showNewsDetail = async (player, k, newsItem, returnPage = 0) => {
const cleanSummary = newsItem.summary.replace(/<[^>]*>/g, ' ').trim();
const detailMessage = `
<div style="font-size: 14px; line-height: 1.6;">
<strong>${newsItem.title}</strong> |
<em>Published: ${formatNewsDate(newsItem.published)}</em> | ${newsItem.link ? `🔗 <a href="${newsItem.link}" target="_blank">Read more</a>` : ''} <br/><br/>
${cleanSummary}
</div>
`;
const options = [
{
value: 'back',
text: '← Back to list',
},
];
showCustomPrompt(
detailMessage,
options,
(selectedValue) => {
setTimeout(async () => {
if (selectedValue === 'back') {
await showNewsList(player, k, returnPage);
}
}, 50);
},
player,
k,
abort
);
};
/**
* Show a list of news articles with pagination (2 at a time)
*/
const showNewsList = async (player, k, page = 0) => {
if (!newsCache) {
newsCache = await fetchNews();
}
if (newsCache.length === 0) {
await displayDialogue({
k,
player,
text: [
'Unable to fetch news at the moment. Please try again later.',
],
});
return;
}
const itemsPerPage = 2;
const totalPages = Math.ceil(newsCache.length / itemsPerPage);
const startIndex = page * itemsPerPage;
const endIndex = Math.min(startIndex + itemsPerPage, newsCache.length);
const currentNews = newsCache.slice(startIndex, endIndex);
const message = `<strong>News (Page ${page + 1}/${totalPages})</strong>`;
// Create options for news items on this page
const options = currentNews.map((news, index) => {
const actualIndex = startIndex + index;
const truncatedTitle =
news.title.length > 50
? news.title.substring(0, 50) + '...'
: news.title;
return {
value: actualIndex,
text: `${actualIndex + 1}. ${truncatedTitle}`,
};
});
// Add navigation buttons
if (page > 0) {
options.push({
value: 'prev',
text: '←',
});
}
if (page < totalPages - 1) {
options.push({
value: 'next',
text: '→',
});
}
options.push({
value: 'close',
text: '✕ Close',
});
showCustomPrompt(
message,
options,
(selectedValue) => {
// Use setTimeout to avoid closing before showing next prompt
setTimeout(async () => {
if (selectedValue === 'prev') {
await showNewsList(player, k, page - 1);
} else if (selectedValue === 'next') {
await showNewsList(player, k, page + 1);
} else if (selectedValue === 'close') {
// Just close, do nothing
return;
} else {
// It's a news index
const selectedNews = newsCache[selectedValue];
await showNewsDetail(player, k, selectedNews, page);
}
}, 50);
},
player,
k,
abort
);
};
export const interactionWithMainboxMainArea = (player, k, map) => {
player.onCollide('mailbox_mainArea', async () => {
time.paused = true;
player.state.isInDialog = true;
abort = new AbortController();
await showNewsList(player, k);
});
};