Skip to content

Commit 1bbc8c3

Browse files
committed
Ropro support
1 parent 617c9ac commit 1bbc8c3

2 files changed

Lines changed: 171 additions & 131 deletions

File tree

src/content/features/profile/groupFilters.js

Lines changed: 165 additions & 130 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { observeElement } from '../../core/observer.js';
1+
import { observeElement, observeChildren } from '../../core/observer.js';
22
import { createPillToggle } from '../../core/ui/general/pillToggle.js';
33
import { getUserIdFromUrl, getGroupIdFromUrl } from '../../core/idExtractor.js';
44
import { callRobloxApiJson } from '../../core/api.js';
@@ -90,151 +90,186 @@ export function init() {
9090
if (!userId) return;
9191

9292
chrome.storage.local.get({ groupFiltersEnabled: true }, (settings) => {
93+
if (!settings.groupFiltersEnabled) return;
94+
9395
observeElement(
9496
'.profile-communities',
9597
(container) => {
96-
const carousel = container.querySelector(
97-
'.css-1i465w8-carousel',
98-
);
99-
if (!carousel) return;
100-
101-
const getItems = () =>
102-
Array.from(
103-
carousel.querySelectorAll('#collection-carousel-item'),
98+
const getCarousel = () => {
99+
const item = container.querySelector(
100+
'#collection-carousel-item, [id="collection-carousel-item"], [class*="-carouselItem"]',
101+
);
102+
return (
103+
item?.parentElement ||
104+
container.querySelector(
105+
'.css-1i465w8-carousel, [class*="-carousel"]',
106+
)
104107
);
108+
};
105109

106-
getItems().forEach((item) => {
107-
const link = item.querySelector('a');
108-
const groupId = getGroupIdFromUrl(
109-
link?.getAttribute('href'),
110+
const setup = () => {
111+
const carousel = getCarousel();
112+
if (!carousel || container.dataset.rovalraFiltersAdded)
113+
return;
114+
115+
const items = Array.from(
116+
carousel.querySelectorAll(
117+
'#collection-carousel-item, [id="collection-carousel-item"], [class*="-carouselItem"]',
118+
),
110119
);
111-
if (groupId) {
112-
getJoinDate(groupId, userId);
113-
}
114-
});
115-
116-
if (
117-
!settings.groupFiltersEnabled ||
118-
container.dataset.rovalraFiltersAdded
119-
)
120-
return;
121-
container.dataset.rovalraFiltersAdded = 'true';
122-
123-
const header = container.querySelector('h2');
124-
if (!header) return;
125-
126-
const headerWrapper = document.createElement('div');
127-
headerWrapper.style.display = 'flex';
128-
headerWrapper.style.alignItems = 'center';
129-
headerWrapper.style.justifyContent = 'space-between';
130-
headerWrapper.style.width = '100%';
131-
headerWrapper.style.marginBottom = '12px';
132-
133-
header.parentNode.insertBefore(headerWrapper, header);
134-
headerWrapper.appendChild(header);
135-
136-
const originalOrder = getItems();
137-
138-
const sortOptions = [
139-
{ text: ts('groupFilters.sort.default'), value: 'default' },
140-
{ text: ts('groupFilters.sort.az'), value: 'az' },
141-
{ text: ts('groupFilters.sort.za'), value: 'za' },
142-
{
143-
text: ts('groupFilters.sort.newest'),
144-
value: 'newest',
145-
tooltip: ts('groupFilters.tooltip'),
146-
},
147-
{
148-
text: ts('groupFilters.sort.oldest'),
149-
value: 'oldest',
150-
tooltip: ts('groupFilters.tooltip'),
151-
},
152-
];
153-
154-
const toggle = createPillToggle({
155-
options: sortOptions,
156-
initialValue: 'default',
157-
onChange: async (value) => {
158-
const items = getItems();
159-
160-
if (value === 'newest' || value === 'oldest') {
161-
await Promise.all(
162-
items.map((item) => {
163-
const link = item.querySelector('a');
164-
const groupId = getGroupIdFromUrl(
165-
link?.getAttribute('href'),
166-
);
167-
return getJoinDate(groupId, userId);
168-
}),
169-
);
120+
121+
if (items.length === 0) return;
122+
123+
container.dataset.rovalraFiltersAdded = 'true';
124+
125+
items.forEach((item) => {
126+
const link = item.querySelector('a');
127+
const groupId = getGroupIdFromUrl(
128+
link?.getAttribute('href'),
129+
);
130+
if (groupId) {
131+
getJoinDate(groupId, userId);
170132
}
133+
});
134+
135+
const header = container.querySelector('h2');
136+
if (!header) return;
137+
138+
const headerWrapper = document.createElement('div');
139+
headerWrapper.style.display = 'flex';
140+
headerWrapper.style.alignItems = 'center';
141+
headerWrapper.style.justifyContent = 'space-between';
142+
headerWrapper.style.width = '100%';
143+
headerWrapper.style.marginBottom = '12px';
144+
145+
header.parentNode.insertBefore(headerWrapper, header);
146+
headerWrapper.appendChild(header);
147+
148+
const originalOrder = [...items];
171149

172-
items.sort((a, b) => {
173-
if (value === 'default') {
174-
return (
175-
originalOrder.indexOf(a) -
176-
originalOrder.indexOf(b)
150+
const sortOptions = [
151+
{
152+
text: ts('groupFilters.sort.default'),
153+
value: 'default',
154+
},
155+
{ text: ts('groupFilters.sort.az'), value: 'az' },
156+
{ text: ts('groupFilters.sort.za'), value: 'za' },
157+
{
158+
text: ts('groupFilters.sort.newest'),
159+
value: 'newest',
160+
tooltip: ts('groupFilters.tooltip'),
161+
},
162+
{
163+
text: ts('groupFilters.sort.oldest'),
164+
value: 'oldest',
165+
tooltip: ts('groupFilters.tooltip'),
166+
},
167+
];
168+
169+
const toggle = createPillToggle({
170+
options: sortOptions,
171+
initialValue: 'default',
172+
onChange: async (value) => {
173+
const activeCarousel = getCarousel();
174+
if (!activeCarousel) return;
175+
176+
const currentItems = Array.from(
177+
activeCarousel.querySelectorAll(
178+
'#collection-carousel-item, [id="collection-carousel-item"], [class*="-carouselItem"]',
179+
),
180+
);
181+
182+
if (value === 'newest' || value === 'oldest') {
183+
await Promise.all(
184+
currentItems.map((item) => {
185+
const link = item.querySelector('a');
186+
const groupId = getGroupIdFromUrl(
187+
link?.getAttribute('href'),
188+
);
189+
return getJoinDate(groupId, userId);
190+
}),
177191
);
178192
}
179193

180-
const nameA =
181-
a
182-
.querySelector('.base-tile-title')
183-
?.textContent?.trim() || '';
184-
const nameB =
185-
b
186-
.querySelector('.base-tile-title')
187-
?.textContent?.trim() || '';
188-
189-
switch (value) {
190-
case 'az':
191-
return nameA.localeCompare(nameB);
192-
case 'za':
193-
return nameB.localeCompare(nameA);
194-
case 'newest': {
195-
const idA = getGroupIdFromUrl(
196-
a
197-
.querySelector('a')
198-
?.getAttribute('href'),
194+
currentItems.sort((a, b) => {
195+
if (value === 'default') {
196+
return (
197+
originalOrder.indexOf(a) -
198+
originalOrder.indexOf(b)
199199
);
200-
const idB = getGroupIdFromUrl(
201-
b
202-
.querySelector('a')
203-
?.getAttribute('href'),
204-
);
205-
const dateA =
206-
joinDateCache.get(idA) || new Date(0);
207-
const dateB =
208-
joinDateCache.get(idB) || new Date(0);
209-
return dateB - dateA;
210200
}
211-
case 'oldest': {
212-
const idA = getGroupIdFromUrl(
213-
a
214-
.querySelector('a')
215-
?.getAttribute('href'),
216-
);
217-
const idB = getGroupIdFromUrl(
218-
b
219-
.querySelector('a')
220-
?.getAttribute('href'),
221-
);
222-
const dateA =
223-
joinDateCache.get(idA) || new Date(0);
224-
const dateB =
225-
joinDateCache.get(idB) || new Date(0);
226-
return dateA - dateB;
201+
202+
const nameA =
203+
a
204+
.querySelector('.base-tile-title')
205+
?.textContent?.trim() || '';
206+
const nameB =
207+
b
208+
.querySelector('.base-tile-title')
209+
?.textContent?.trim() || '';
210+
211+
switch (value) {
212+
case 'az':
213+
return nameA.localeCompare(nameB);
214+
case 'za':
215+
return nameB.localeCompare(nameA);
216+
case 'newest': {
217+
const idA = getGroupIdFromUrl(
218+
a
219+
.querySelector('a')
220+
?.getAttribute('href'),
221+
);
222+
const idB = getGroupIdFromUrl(
223+
b
224+
.querySelector('a')
225+
?.getAttribute('href'),
226+
);
227+
const dateA =
228+
joinDateCache.get(idA) ||
229+
new Date(0);
230+
const dateB =
231+
joinDateCache.get(idB) ||
232+
new Date(0);
233+
return dateB - dateA;
234+
}
235+
case 'oldest': {
236+
const idA = getGroupIdFromUrl(
237+
a
238+
.querySelector('a')
239+
?.getAttribute('href'),
240+
);
241+
const idB = getGroupIdFromUrl(
242+
b
243+
.querySelector('a')
244+
?.getAttribute('href'),
245+
);
246+
const dateA =
247+
joinDateCache.get(idA) ||
248+
new Date(0);
249+
const dateB =
250+
joinDateCache.get(idB) ||
251+
new Date(0);
252+
return dateA - dateB;
253+
}
254+
default:
255+
return 0;
227256
}
228-
default:
229-
return 0;
230-
}
231-
});
257+
});
258+
259+
activeCarousel.style.display = 'flex';
260+
activeCarousel.style.flexWrap = 'nowrap';
261+
262+
currentItems.forEach((item) =>
263+
activeCarousel.appendChild(item),
264+
);
265+
},
266+
});
232267

233-
items.forEach((item) => carousel.appendChild(item));
234-
},
235-
});
268+
headerWrapper.appendChild(toggle);
269+
};
236270

237-
headerWrapper.appendChild(toggle);
271+
setup();
272+
observeChildren(container, setup);
238273
},
239274
{ multiple: true },
240275
);

src/content/features/profile/grouprole.js

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,8 +41,13 @@ export function init() {
4141
const groupRoleEnabled = settings.groupRoleEnabled;
4242
const groupJoinedDateEnabled = settings.groupJoinedDateEnabled;
4343

44+
const itemSelector = [
45+
'[class*="-carousel"] [id="collection-carousel-item"] .base-tile a[href*="/communities/"]',
46+
'[class*="-carousel"] [class*="-carouselItem"] .base-tile a[href*="/communities/"]',
47+
].join(', ');
48+
4449
observeElement(
45-
'.css-1i465w8-carousel #collection-carousel-item .base-tile a[href*="/communities/"]',
50+
itemSelector,
4651
async (groupLink) => {
4752
if (groupLink.dataset.rovalraGroupRoleProcessed) return;
4853
groupLink.dataset.rovalraGroupRoleProcessed = 'true';

0 commit comments

Comments
 (0)