Merge remote-tracking branch 'soapbox/develop' into rss-button
|
@ -28,6 +28,8 @@ busybox unzip soapbox.zip -o -d /opt/pleroma/instance
|
|||
The change will take effect immediately, just refresh your browser tab.
|
||||
It's not necessary to restart the Pleroma service.
|
||||
|
||||
***For OTP releases,*** *unpack to /var/lib/pleroma instead.*
|
||||
|
||||
To remove Soapbox and revert to the default pleroma-fe, simply `rm /opt/pleroma/instance/static/index.html` (you can delete other stuff in there too, but be careful not to delete your own HTML files).
|
||||
|
||||
## :elephant: Deploy on Mastodon
|
||||
|
|
|
@ -1,10 +1,10 @@
|
|||
import loadPolyfills from './soapbox/load_polyfills';
|
||||
import loadPolyfills from './soapbox/load-polyfills';
|
||||
|
||||
// Load iframe event listener
|
||||
require('./soapbox/iframe');
|
||||
|
||||
// @ts-ignore
|
||||
require.context('./images/', true);
|
||||
require.context('./assets/images/', true);
|
||||
|
||||
// Load stylesheet
|
||||
require('react-datepicker/dist/react-datepicker.css');
|
||||
|
|
Przed Szerokość: | Wysokość: | Rozmiar: 6.0 KiB Po Szerokość: | Wysokość: | Rozmiar: 6.0 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 3.3 KiB Po Szerokość: | Wysokość: | Rozmiar: 3.3 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 302 B Po Szerokość: | Wysokość: | Rozmiar: 302 B |
Przed Szerokość: | Wysokość: | Rozmiar: 4.8 KiB Po Szerokość: | Wysokość: | Rozmiar: 4.8 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 4.0 KiB Po Szerokość: | Wysokość: | Rozmiar: 4.0 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 2.2 KiB Po Szerokość: | Wysokość: | Rozmiar: 2.2 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 81 B Po Szerokość: | Wysokość: | Rozmiar: 81 B |
Przed Szerokość: | Wysokość: | Rozmiar: 812 B Po Szerokość: | Wysokość: | Rozmiar: 812 B |
Przed Szerokość: | Wysokość: | Rozmiar: 812 B Po Szerokość: | Wysokość: | Rozmiar: 812 B |
Przed Szerokość: | Wysokość: | Rozmiar: 3.4 KiB Po Szerokość: | Wysokość: | Rozmiar: 3.4 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 99 B Po Szerokość: | Wysokość: | Rozmiar: 99 B |
Przed Szerokość: | Wysokość: | Rozmiar: 1.3 KiB Po Szerokość: | Wysokość: | Rozmiar: 1.3 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 1.0 KiB Po Szerokość: | Wysokość: | Rozmiar: 1.0 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 811 B Po Szerokość: | Wysokość: | Rozmiar: 811 B |
Przed Szerokość: | Wysokość: | Rozmiar: 221 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 69 KiB |
|
@ -1,69 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="63.161953mm"
|
||||
height="181.12712mm"
|
||||
viewBox="0 0 63.161953 181.12712"
|
||||
version="1.1"
|
||||
id="svg1199"
|
||||
inkscape:version="0.92.4 (unknown)"
|
||||
sodipodi:docname="spider.svg">
|
||||
<defs
|
||||
id="defs1193" />
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.35355339"
|
||||
inkscape:cx="188.63933"
|
||||
inkscape:cy="154.00309"
|
||||
inkscape:document-units="mm"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1366"
|
||||
inkscape:window-height="705"
|
||||
inkscape:window-x="0"
|
||||
inkscape:window-y="30"
|
||||
inkscape:window-maximized="1"
|
||||
inkscape:snap-global="false"
|
||||
fit-margin-top="0"
|
||||
fit-margin-left="0"
|
||||
fit-margin-right="0"
|
||||
fit-margin-bottom="0" />
|
||||
<metadata
|
||||
id="metadata1196">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(-54.223528,-39.965002)">
|
||||
<path
|
||||
style="stroke-width:0.99999994"
|
||||
d="m 329.96094,151.04883 -7.95132,372.20898 c -30.02705,2.9243 -45.57271,12.92382 -64.25977,32.67188 -25.16762,33.38088 -18.43249,69.4298 -0.4707,100.66992 12.24879,17.03193 32.3984,27.97627 53.07033,34.15036 0,0 -5.52814,0.0857 -11.58984,9.46094 -18.91001,-5.43999 -38.07073,-9.95039 -57.14063,-14.82032 -10.49976,0.9523 -28.58163,18.8274 -36.67969,24.9004 0.27746,13.19067 1.67361,27.14135 3.33008,39.15039 1.1699,-1.57002 0.83916,-3.5804 1.03906,-5.40039 0.9,-10.79003 0.60034,-21.66016 1.99024,-32.41016 9.28,-6.03999 17.7906,-13.20072 26.7207,-19.7207 18.99884,1.97067 39.37112,9.36858 55.91016,13.35156 -0.49,2.41999 -1.38047,5.27974 -4.23047,5.67969 -18.4,4.60002 -36.81969,9.10007 -55.17969,13.83007 -4.86555,6.81697 -23.47884,41.76065 -22.16992,48 3.32807,9.25919 3.76668,29.35751 8.58984,35.70899 -0.65616,-11.27353 -1.26587,-23.12102 -2.88086,-33.41016 4.366,-15.53732 14.77165,-31.85507 21.21094,-44.72851 16.36837,-5.03014 33.6873,-8.93673 49.58008,-11.32032 -0.0299,3.31998 -0.081,6.66013 -0.20117,9.99024 -10.89612,8.5036 -30.45632,23.65603 -40.40821,30.44922 -2.57681,15.80044 -3.38605,33.75066 -4.2207,48.55078 2.50279,8.85582 13.19431,23.74406 18.17156,23.90823 -2.93816,-7.30216 -8.51629,-14.68425 -10.88086,-21.31836 -0.17087,-16.87764 2.99403,-32.98356 3.70114,-48.41015 11.61344,-9.80937 25.4679,-15.10577 35.89062,-24.25 2.26541,6.18864 7.32913,9.97253 10.32813,15.05859 -2.15,3.10001 -5.51922,5.79 -5.94922,9.75 2.88,4.37998 6.60955,8.25101 10.68945,11.54102 -0.85,-3.43 -2.26023,-6.68056 -3.24023,-10.06055 l 6.20117,-7.18945 c 10.18753,5.69922 19.39911,4.81707 28.78906,0.75976 2.12,2.45 4.30149,5.11952 5.27149,8.26953 -0.85,3.26 -2.7418,6.14966 -3.5918,9.42969 4.21,-3.40003 8.09071,-7.32883 11.4707,-11.54883 -0.72,-4.08 -4.4693,-6.80104 -5.27929,-10.79101 3.66,-4.43003 7.97023,-8.42941 10.24023,-13.85938 5.68622,5.4072 34.43902,22.24881 34.94922,26.88086 0.36518,16.19209 3.11897,31.74502 2,46.75 -4.46916,8.68536 -7.12999,16.57554 -14.39063,22.67969 9.90723,0.50906 17.4253,-14.74937 21.52152,-22.69328 -0.18697,-17.91233 -0.74645,-33.39521 -1.16992,-49.66992 -13.47001,-10.57002 -27.16094,-20.89017 -40.46094,-31.66016 0.59,-3.81003 0.49976,-7.6583 0.50977,-11.48828 15.73,4.66001 31.80992,8.14868 47.66992,12.38867 7.58475,10.99663 15.5151,31.43552 20.24023,42.75977 0.43698,13.66208 -3.68079,27.5449 -4.08008,40.14062 1.49998,-1.33999 1.6498,-3.42013 2.17969,-5.24023 1.88197,-11.16719 9.61842,-29.63645 8.13086,-37.92969 -6.21997,-14.23003 -11.95978,-28.75009 -18.42969,-42.83008 -19.30273,-6.68031 -40.27482,-12.85569 -58.39062,-17.73047 -0.65,-1.72002 -1.1801,-3.47951 -1.5,-5.26953 17.78,-3.66999 35.60009,-7.40034 53.33008,-11.32031 5.35892,-0.14205 29.14876,22.09172 28.98047,23.98047 1.30016,6.78634 -2.08415,29.71011 1.61914,33.13086 2.05988,-11.02999 3.41097,-22.17002 5.12109,-33.25 -0.32862,-6.33401 -29.16337,-28.29439 -33.91016,-30.79102 -20.42635,4.13166 -40.67884,9.74123 -59.80078,12.63086 -5.16629,-4.96887 -11.64306,-7.41991 -17.4707,-10.33984 26.33,-1.87998 52.09,-16.02008 66.25,-38.58008 9.5235,-13.96814 12.87637,-29.769 13.1992,-45.79102 0.33714,-20.46694 -8.12112,-40.39069 -21.6211,-55.4707 -18.78284,-17.43524 -31.48782,-23.12017 -55.43945,-26.73828 l 6.93151,-372.80078 z"
|
||||
id="path1768"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccc"
|
||||
transform="scale(0.26458333)" />
|
||||
</g>
|
||||
</svg>
|
Przed Szerokość: | Wysokość: | Rozmiar: 5.2 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 77 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 12 KiB |
|
@ -1,34 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<svg xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:cc="http://creativecommons.org/ns#" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:svg="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1" id="svg46269" viewBox="0 0 340.00001 394.2857" height="111.27618mm" width="95.955559mm">
|
||||
<defs id="defs46271">
|
||||
<linearGradient id="linearGradient46839">
|
||||
<stop id="stop46841" offset="0" style="stop-color:#904700;stop-opacity:1;"/>
|
||||
<stop id="stop46843" offset="1" style="stop-color:#904700;stop-opacity:0;"/>
|
||||
</linearGradient>
|
||||
<linearGradient id="linearGradient46831">
|
||||
<stop id="stop46833" offset="0" style="stop-color:#904700;stop-opacity:1;"/>
|
||||
<stop id="stop46835" offset="1" style="stop-color:#904700;stop-opacity:0;"/>
|
||||
</linearGradient>
|
||||
<linearGradient id="linearGradient46823">
|
||||
<stop id="stop46825" offset="0" style="stop-color:#904700;stop-opacity:1;"/>
|
||||
<stop id="stop46827" offset="1" style="stop-color:#904700;stop-opacity:0;"/>
|
||||
</linearGradient>
|
||||
<radialGradient gradientTransform="matrix(4.9019612,0,0,4.9019612,-600.72836,-1264.1473)" gradientUnits="userSpaceOnUse" r="72.85714" fy="330.93362" fx="152.85715" cy="330.93362" cx="152.85715" id="radialGradient46829" xlink:href="#linearGradient46823"/>
|
||||
<radialGradient gradientTransform="matrix(3.3636365,0,0,3.3636365,-602.85717,-938.05096)" gradientUnits="userSpaceOnUse" r="62.857143" fy="429.50507" fx="251.42857" cy="429.50507" cx="251.42857" id="radialGradient46837" xlink:href="#linearGradient46831"/>
|
||||
<radialGradient gradientTransform="matrix(1.7317072,0,0,1.7317072,-145.78397,-287.44272)" gradientUnits="userSpaceOnUse" r="58.57143" fy="470.93369" fx="132.85715" cy="470.93369" cx="132.85715" id="radialGradient46845" xlink:href="#linearGradient46839"/>
|
||||
</defs>
|
||||
<metadata id="metadata46274">
|
||||
<rdf:RDF>
|
||||
<cc:Work rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type rdf:resource="http://purl.org/dc/dcmitype/StillImage"/>
|
||||
<dc:title/>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g transform="translate(-8.5714264,-218.07648)" id="layer1">
|
||||
<circle r="140" cy="358.07648" cx="148.57143" id="path46817" style="color:#000000;display:inline;overflow:visible;visibility:visible;fill:url(#radialGradient46829);fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:20, 5;stroke-dashoffset:0;stroke-opacity:1;marker:none;enable-background:accumulate"/>
|
||||
<circle r="105.71429" cy="506.64789" cx="242.85715" id="path46819" style="color:#000000;display:inline;overflow:visible;visibility:visible;fill:url(#radialGradient46837);fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:20, 5;stroke-dashoffset:0;stroke-opacity:1;marker:none;enable-background:accumulate"/>
|
||||
<circle r="58.57143" cy="528.07654" cx="84.285713" id="path46821" style="color:#000000;display:inline;overflow:visible;visibility:visible;fill:url(#radialGradient46845);fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:20, 5;stroke-dashoffset:0;stroke-opacity:1;marker:none;enable-background:accumulate"/>
|
||||
</g>
|
||||
</svg>
|
Przed Szerokość: | Wysokość: | Rozmiar: 3.4 KiB |
Przed Szerokość: | Wysokość: | Rozmiar: 10 KiB |
|
@ -87,7 +87,7 @@
|
|||
"compose_form.poll.add_option": "Add a choice",
|
||||
"compose_form.poll.duration": "Poll duration",
|
||||
"compose_form.poll.option_placeholder": "Choice {number}",
|
||||
"compose_form.poll.remove_option": "Remove this choice",
|
||||
"compose_form.poll.remove_option": "Delete",
|
||||
"compose_form.poll.type.hint": "Click to toggle poll type. Radio button (default) is single. Checkbox is multiple.",
|
||||
"compose_form.publish": "Publish",
|
||||
"compose_form.publish_loud": "{publish}!",
|
||||
|
@ -319,6 +319,7 @@
|
|||
"poll_button.add_poll": "Add a poll",
|
||||
"poll_button.remove_poll": "Remove poll",
|
||||
"preferences.fields.auto_play_gif_label": "Auto-play animated GIFs",
|
||||
"preferences.fields.auto_play_video_label": "Auto-play videos",
|
||||
"preferences.fields.boost_modal_label": "Show confirmation dialog before reposting",
|
||||
"preferences.fields.delete_modal_label": "Show confirmation dialog before deleting a post",
|
||||
"preferences.fields.demetricator_label": "Use Demetricator",
|
||||
|
@ -565,7 +566,7 @@
|
|||
"compose_form.poll.add_option": "Add a choice",
|
||||
"compose_form.poll.duration": "Poll duration",
|
||||
"compose_form.poll.option_placeholder": "Choice {number}",
|
||||
"compose_form.poll.remove_option": "Remove this choice",
|
||||
"compose_form.poll.remove_option": "Delete",
|
||||
"compose_form.poll.type.hint": "Click to toggle poll type. Radio button (default) is single. Checkbox is multiple.",
|
||||
"compose_form.publish": "Publish",
|
||||
"compose_form.publish_loud": "{publish}!",
|
||||
|
|
|
@ -2,7 +2,7 @@ import { Map as ImmutableMap } from 'immutable';
|
|||
|
||||
import { __stub } from 'soapbox/api';
|
||||
import { mockStore, rootState } from 'soapbox/jest/test-helpers';
|
||||
import { ReducerRecord, EditRecord } from 'soapbox/reducers/account_notes';
|
||||
import { ReducerRecord, EditRecord } from 'soapbox/reducers/account-notes';
|
||||
|
||||
import { normalizeAccount, normalizeRelationship } from '../../normalizers';
|
||||
import { changeAccountNoteComment, initAccountNoteModal, submitAccountNote } from '../account-notes';
|
||||
|
|
|
@ -2,7 +2,7 @@ import { Map as ImmutableMap } from 'immutable';
|
|||
|
||||
import { __stub } from 'soapbox/api';
|
||||
import { mockStore, rootState } from 'soapbox/jest/test-helpers';
|
||||
import { ListRecord, ReducerRecord } from 'soapbox/reducers/user_lists';
|
||||
import { ListRecord, ReducerRecord } from 'soapbox/reducers/user-lists';
|
||||
|
||||
import { normalizeAccount, normalizeInstance, normalizeRelationship } from '../../normalizers';
|
||||
import {
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import { __stub } from 'soapbox/api';
|
||||
import { mockStore, rootState } from 'soapbox/jest/test-helpers';
|
||||
import { ListRecord, ReducerRecord as UserListsRecord } from 'soapbox/reducers/user_lists';
|
||||
import { ListRecord, ReducerRecord as UserListsRecord } from 'soapbox/reducers/user-lists';
|
||||
|
||||
import { expandBlocks, fetchBlocks } from '../blocks';
|
||||
|
||||
|
|
|
@ -7,7 +7,7 @@ import {
|
|||
fetchMe, patchMe,
|
||||
} from '../me';
|
||||
|
||||
jest.mock('../../storage/kv_store', () => ({
|
||||
jest.mock('../../storage/kv-store', () => ({
|
||||
__esModule: true,
|
||||
default: {
|
||||
getItemOrError: jest.fn().mockReturnValue(Promise.resolve({})),
|
||||
|
|
|
@ -16,7 +16,8 @@ import { obtainOAuthToken, revokeOAuthToken } from 'soapbox/actions/oauth';
|
|||
import { startOnboarding } from 'soapbox/actions/onboarding';
|
||||
import snackbar from 'soapbox/actions/snackbar';
|
||||
import { custom } from 'soapbox/custom';
|
||||
import KVStore from 'soapbox/storage/kv_store';
|
||||
import { queryClient } from 'soapbox/queries/client';
|
||||
import KVStore from 'soapbox/storage/kv-store';
|
||||
import { getLoggedInAccount, parseBaseURL } from 'soapbox/utils/auth';
|
||||
import sourceCode from 'soapbox/utils/code';
|
||||
import { getFeatures } from 'soapbox/utils/features';
|
||||
|
@ -239,15 +240,25 @@ export const logOut = () =>
|
|||
token: state.auth.getIn(['users', account.url, 'access_token']),
|
||||
};
|
||||
|
||||
return dispatch(revokeOAuthToken(params)).finally(() => {
|
||||
dispatch({ type: AUTH_LOGGED_OUT, account, standalone });
|
||||
return dispatch(snackbar.success(messages.loggedOut));
|
||||
});
|
||||
return dispatch(revokeOAuthToken(params))
|
||||
.finally(() => {
|
||||
// Clear all stored cache from React Query
|
||||
queryClient.invalidateQueries();
|
||||
queryClient.clear();
|
||||
|
||||
dispatch({ type: AUTH_LOGGED_OUT, account, standalone });
|
||||
|
||||
return dispatch(snackbar.success(messages.loggedOut));
|
||||
});
|
||||
};
|
||||
|
||||
export const switchAccount = (accountId: string, background = false) =>
|
||||
(dispatch: AppDispatch, getState: () => RootState) => {
|
||||
const account = getState().accounts.get(accountId);
|
||||
// Clear all stored cache from React Query
|
||||
queryClient.invalidateQueries();
|
||||
queryClient.clear();
|
||||
|
||||
return dispatch({ type: SWITCH_ACCOUNT, account, background });
|
||||
};
|
||||
|
||||
|
|
|
@ -5,12 +5,12 @@ import { defineMessages, IntlShape } from 'react-intl';
|
|||
|
||||
import snackbar from 'soapbox/actions/snackbar';
|
||||
import api from 'soapbox/api';
|
||||
import { search as emojiSearch } from 'soapbox/features/emoji/emoji_mart_search_light';
|
||||
import { search as emojiSearch } from 'soapbox/features/emoji/emoji-mart-search-light';
|
||||
import { tagHistory } from 'soapbox/settings';
|
||||
import { isLoggedIn } from 'soapbox/utils/auth';
|
||||
import { getFeatures, parseVersion } from 'soapbox/utils/features';
|
||||
import { formatBytes, getVideoDuration } from 'soapbox/utils/media';
|
||||
import resizeImage from 'soapbox/utils/resize_image';
|
||||
import resizeImage from 'soapbox/utils/resize-image';
|
||||
|
||||
import { showAlert, showAlertForError } from './alerts';
|
||||
import { useEmoji } from './emojis';
|
||||
|
@ -21,8 +21,8 @@ import { getSettings } from './settings';
|
|||
import { createStatus } from './statuses';
|
||||
|
||||
import type { History } from 'history';
|
||||
import type { Emoji } from 'soapbox/components/autosuggest_emoji';
|
||||
import type { AutoSuggestion } from 'soapbox/components/autosuggest_input';
|
||||
import type { Emoji } from 'soapbox/components/autosuggest-emoji';
|
||||
import type { AutoSuggestion } from 'soapbox/components/autosuggest-input';
|
||||
import type { AppDispatch, RootState } from 'soapbox/store';
|
||||
import type { Account, APIEntity, Status, Tag } from 'soapbox/types/entities';
|
||||
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import axios from 'axios';
|
||||
|
||||
import * as BuildConfig from 'soapbox/build_config';
|
||||
import * as BuildConfig from 'soapbox/build-config';
|
||||
import { isURL } from 'soapbox/utils/auth';
|
||||
import sourceCode from 'soapbox/utils/code';
|
||||
import { getFeatures } from 'soapbox/utils/features';
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import type { DropdownPlacement } from 'soapbox/components/dropdown_menu';
|
||||
import type { DropdownPlacement } from 'soapbox/components/dropdown-menu';
|
||||
|
||||
const DROPDOWN_MENU_OPEN = 'DROPDOWN_MENU_OPEN';
|
||||
const DROPDOWN_MENU_CLOSE = 'DROPDOWN_MENU_CLOSE';
|
|
@ -1,6 +1,6 @@
|
|||
import { saveSettings } from './settings';
|
||||
|
||||
import type { Emoji } from 'soapbox/components/autosuggest_emoji';
|
||||
import type { Emoji } from 'soapbox/components/autosuggest-emoji';
|
||||
import type { AppDispatch } from 'soapbox/store';
|
||||
|
||||
const EMOJI_USE = 'EMOJI_USE';
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import { createAsyncThunk } from '@reduxjs/toolkit';
|
||||
import get from 'lodash/get';
|
||||
|
||||
import KVStore from 'soapbox/storage/kv_store';
|
||||
import KVStore from 'soapbox/storage/kv-store';
|
||||
import { RootState } from 'soapbox/store';
|
||||
import { getAuthUserUrl } from 'soapbox/utils/auth';
|
||||
import { parseVersion } from 'soapbox/utils/features';
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import KVStore from 'soapbox/storage/kv_store';
|
||||
import KVStore from 'soapbox/storage/kv-store';
|
||||
import { getAuthUserId, getAuthUserUrl } from 'soapbox/utils/auth';
|
||||
|
||||
import api from '../api';
|
||||
|
|
|
@ -1,8 +1,10 @@
|
|||
import type { ModalType } from 'soapbox/features/ui/components/modal-root';
|
||||
|
||||
export const MODAL_OPEN = 'MODAL_OPEN';
|
||||
export const MODAL_CLOSE = 'MODAL_CLOSE';
|
||||
|
||||
/** Open a modal of the given type */
|
||||
export function openModal(type: string, props?: any) {
|
||||
export function openModal(type: ModalType, props?: any) {
|
||||
return {
|
||||
type: MODAL_OPEN,
|
||||
modalType: type,
|
||||
|
@ -11,7 +13,7 @@ export function openModal(type: string, props?: any) {
|
|||
}
|
||||
|
||||
/** Close the modal */
|
||||
export function closeModal(type?: string) {
|
||||
export function closeModal(type?: ModalType) {
|
||||
return {
|
||||
type: MODAL_CLOSE,
|
||||
modalType: type,
|
||||
|
|
|
@ -7,7 +7,7 @@ import { openModal } from 'soapbox/actions/modals';
|
|||
import snackbar from 'soapbox/actions/snackbar';
|
||||
import OutlineBox from 'soapbox/components/outline-box';
|
||||
import { Stack, Text } from 'soapbox/components/ui';
|
||||
import AccountContainer from 'soapbox/containers/account_container';
|
||||
import AccountContainer from 'soapbox/containers/account-container';
|
||||
import { isLocal } from 'soapbox/utils/accounts';
|
||||
|
||||
import type { AppDispatch, RootState } from 'soapbox/store';
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
import { Map as ImmutableMap, Set as ImmutableSet } from 'immutable';
|
||||
|
||||
import ConfigDB from 'soapbox/utils/config_db';
|
||||
import ConfigDB from 'soapbox/utils/config-db';
|
||||
|
||||
import { fetchConfig, updateConfig } from './admin';
|
||||
|
||||
import type { AppDispatch, RootState } from 'soapbox/store';
|
||||
import type { Policy } from 'soapbox/utils/config_db';
|
||||
import type { Policy } from 'soapbox/utils/config-db';
|
||||
|
||||
const simplePolicyMerge = (simplePolicy: Policy, host: string, restrictions: ImmutableMap<string, any>) => {
|
||||
return simplePolicy.map((hosts, key) => {
|
||||
|
|
|
@ -1,14 +1,11 @@
|
|||
import {
|
||||
Map as ImmutableMap,
|
||||
} from 'immutable';
|
||||
import IntlMessageFormat from 'intl-messageformat';
|
||||
import 'intl-pluralrules';
|
||||
import { defineMessages } from 'react-intl';
|
||||
|
||||
import api, { getLinks } from 'soapbox/api';
|
||||
import compareId from 'soapbox/compare_id';
|
||||
import { getFilters, regexFromFilters } from 'soapbox/selectors';
|
||||
import { isLoggedIn } from 'soapbox/utils/auth';
|
||||
import { compareId } from 'soapbox/utils/comparators';
|
||||
import { getFeatures, parseVersion, PLEROMA } from 'soapbox/utils/features';
|
||||
import { unescapeHTML } from 'soapbox/utils/html';
|
||||
import { EXCLUDE_TYPES, NOTIFICATION_TYPES } from 'soapbox/utils/notification';
|
||||
|
@ -149,13 +146,13 @@ const updateNotificationsQueue = (notification: APIEntity, intlMessages: Record<
|
|||
|
||||
const dequeueNotifications = () =>
|
||||
(dispatch: AppDispatch, getState: () => RootState) => {
|
||||
const queuedNotifications = getState().notifications.get('queuedNotifications');
|
||||
const totalQueuedNotificationsCount = getState().notifications.get('totalQueuedNotificationsCount');
|
||||
const queuedNotifications = getState().notifications.queuedNotifications;
|
||||
const totalQueuedNotificationsCount = getState().notifications.totalQueuedNotificationsCount;
|
||||
|
||||
if (totalQueuedNotificationsCount === 0) {
|
||||
return;
|
||||
} else if (totalQueuedNotificationsCount > 0 && totalQueuedNotificationsCount <= MAX_QUEUED_NOTIFICATIONS) {
|
||||
queuedNotifications.forEach((block: APIEntity) => {
|
||||
queuedNotifications.forEach((block) => {
|
||||
dispatch(updateNotifications(block.notification));
|
||||
});
|
||||
} else {
|
||||
|
@ -184,7 +181,7 @@ const expandNotifications = ({ maxId }: Record<string, any> = {}, done: () => an
|
|||
const notifications = state.notifications;
|
||||
const isLoadingMore = !!maxId;
|
||||
|
||||
if (notifications.get('isLoading')) {
|
||||
if (notifications.isLoading) {
|
||||
done();
|
||||
return dispatch(noOp);
|
||||
}
|
||||
|
@ -207,7 +204,7 @@ const expandNotifications = ({ maxId }: Record<string, any> = {}, done: () => an
|
|||
}
|
||||
}
|
||||
|
||||
if (!maxId && notifications.get('items').size > 0) {
|
||||
if (!maxId && notifications.items.size > 0) {
|
||||
params.since_id = notifications.getIn(['items', 0, 'id']);
|
||||
}
|
||||
|
||||
|
@ -306,8 +303,8 @@ const markReadNotifications = () =>
|
|||
if (!isLoggedIn(getState)) return;
|
||||
|
||||
const state = getState();
|
||||
const topNotificationId: string | undefined = state.notifications.get('items').first(ImmutableMap()).get('id');
|
||||
const lastReadId: string | -1 = state.notifications.get('lastRead');
|
||||
const topNotificationId = state.notifications.items.first()?.id;
|
||||
const lastReadId = state.notifications.lastRead;
|
||||
const v = parseVersion(state.instance.version);
|
||||
|
||||
if (topNotificationId && (lastReadId === -1 || compareId(topNotificationId, lastReadId) > 0)) {
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { createPushSubscription, updatePushSubscription } from 'soapbox/actions/push_subscriptions';
|
||||
import { createPushSubscription, updatePushSubscription } from 'soapbox/actions/push-subscriptions';
|
||||
import { pushNotificationsSetting } from 'soapbox/settings';
|
||||
import { getVapidKey } from 'soapbox/utils/auth';
|
||||
import { decode as decodeBase64 } from 'soapbox/utils/base64';
|
|
@ -2,7 +2,7 @@ import { createSelector } from 'reselect';
|
|||
|
||||
import { getHost } from 'soapbox/actions/instance';
|
||||
import { normalizeSoapboxConfig } from 'soapbox/normalizers';
|
||||
import KVStore from 'soapbox/storage/kv_store';
|
||||
import KVStore from 'soapbox/storage/kv-store';
|
||||
import { removeVS16s } from 'soapbox/utils/emoji';
|
||||
import { getFeatures } from 'soapbox/utils/features';
|
||||
|
||||
|
|
|
@ -4,7 +4,7 @@ import LinkHeader from 'http-link-header';
|
|||
|
||||
import type { AxiosInstance, AxiosResponse } from 'axios';
|
||||
|
||||
const api = jest.requireActual('../api') as Record<string, Function>;
|
||||
const api = jest.requireActual('../index') as Record<string, Function>;
|
||||
let mocks: Array<Function> = [];
|
||||
|
||||
export const __stub = (func: (mock: MockAdapter) => void) => mocks.push(func);
|
|
@ -9,18 +9,18 @@ import axios, { AxiosInstance, AxiosResponse } from 'axios';
|
|||
import LinkHeader from 'http-link-header';
|
||||
import { createSelector } from 'reselect';
|
||||
|
||||
import * as BuildConfig from 'soapbox/build_config';
|
||||
import * as BuildConfig from 'soapbox/build-config';
|
||||
import { RootState } from 'soapbox/store';
|
||||
import { getAccessToken, getAppToken, isURL, parseBaseURL } from 'soapbox/utils/auth';
|
||||
|
||||
import type MockAdapter from 'axios-mock-adapter';
|
||||
|
||||
/**
|
||||
Parse Link headers, mostly for pagination.
|
||||
@see {@link https://www.npmjs.com/package/http-link-header}
|
||||
@param {object} response - Axios response object
|
||||
@returns {object} Link object
|
||||
*/
|
||||
Parse Link headers, mostly for pagination.
|
||||
@see {@link https://www.npmjs.com/package/http-link-header}
|
||||
@param {object} response - Axios response object
|
||||
@returns {object} Link object
|
||||
*/
|
||||
export const getLinks = (response: AxiosResponse): LinkHeader => {
|
||||
return new LinkHeader(response.headers?.link);
|
||||
};
|
||||
|
@ -50,11 +50,11 @@ const getAuthBaseURL = createSelector([
|
|||
});
|
||||
|
||||
/**
|
||||
* Base client for HTTP requests.
|
||||
* @param {string} accessToken
|
||||
* @param {string} baseURL
|
||||
* @returns {object} Axios instance
|
||||
*/
|
||||
* Base client for HTTP requests.
|
||||
* @param {string} accessToken
|
||||
* @param {string} baseURL
|
||||
* @returns {object} Axios instance
|
||||
*/
|
||||
export const baseClient = (accessToken?: string | null, baseURL: string = ''): AxiosInstance => {
|
||||
return axios.create({
|
||||
// When BACKEND_URL is set, always use it.
|
||||
|
@ -68,22 +68,22 @@ export const baseClient = (accessToken?: string | null, baseURL: string = ''): A
|
|||
};
|
||||
|
||||
/**
|
||||
* Dumb client for grabbing static files.
|
||||
* It uses FE_SUBDIRECTORY and parses JSON if possible.
|
||||
* No authorization is needed.
|
||||
*/
|
||||
* Dumb client for grabbing static files.
|
||||
* It uses FE_SUBDIRECTORY and parses JSON if possible.
|
||||
* No authorization is needed.
|
||||
*/
|
||||
export const staticClient = axios.create({
|
||||
baseURL: BuildConfig.FE_SUBDIRECTORY,
|
||||
transformResponse: [maybeParseJSON],
|
||||
});
|
||||
|
||||
/**
|
||||
* Stateful API client.
|
||||
* Uses credentials from the Redux store if available.
|
||||
* @param {function} getState - Must return the Redux state
|
||||
* @param {string} authType - Either 'user' or 'app'
|
||||
* @returns {object} Axios instance
|
||||
*/
|
||||
* Stateful API client.
|
||||
* Uses credentials from the Redux store if available.
|
||||
* @param {function} getState - Must return the Redux state
|
||||
* @param {string} authType - Either 'user' or 'app'
|
||||
* @returns {object} Axios instance
|
||||
*/
|
||||
export default (getState: () => RootState, authType: string = 'user'): AxiosInstance => {
|
||||
const state = getState();
|
||||
const accessToken = getToken(state, authType);
|
|
@ -1,7 +1,7 @@
|
|||
// @preval
|
||||
/**
|
||||
* Build config: configuration set at build time.
|
||||
* @module soapbox/build_config
|
||||
* @module soapbox/build-config
|
||||
*/
|
||||
|
||||
const trim = require('lodash/trim');
|
|
@ -1,7 +1,7 @@
|
|||
import React from 'react';
|
||||
|
||||
import { render, screen } from '../../jest/test-helpers';
|
||||
import AutosuggestEmoji from '../autosuggest_emoji';
|
||||
import AutosuggestEmoji from '../autosuggest-emoji';
|
||||
|
||||
describe('<AutosuggestEmoji />', () => {
|
||||
it('renders native emoji', () => {
|
|
@ -3,7 +3,7 @@ import React from 'react';
|
|||
import { normalizeAccount } from 'soapbox/normalizers';
|
||||
|
||||
import { render, screen } from '../../jest/test-helpers';
|
||||
import AvatarOverlay from '../avatar_overlay';
|
||||
import AvatarOverlay from '../avatar-overlay';
|
||||
|
||||
import type { ReducerAccount } from 'soapbox/reducers/accounts';
|
||||
|
|
@ -1,7 +1,7 @@
|
|||
import React from 'react';
|
||||
|
||||
import { render, screen } from '../../jest/test-helpers';
|
||||
import EmojiSelector from '../emoji_selector';
|
||||
import EmojiSelector from '../emoji-selector';
|
||||
|
||||
describe('<EmojiSelector />', () => {
|
||||
it('renders correctly', () => {
|
|
@ -2,7 +2,7 @@ import classNames from 'clsx';
|
|||
import React, { useState } from 'react';
|
||||
import { defineMessages, useIntl } from 'react-intl';
|
||||
|
||||
import AutosuggestAccountInput from 'soapbox/components/autosuggest_account_input';
|
||||
import AutosuggestAccountInput from 'soapbox/components/autosuggest-account-input';
|
||||
import Icon from 'soapbox/components/icon';
|
||||
|
||||
const messages = defineMessages({
|
|
@ -1,8 +1,8 @@
|
|||
import * as React from 'react';
|
||||
import { Link, useHistory } from 'react-router-dom';
|
||||
|
||||
import HoverRefWrapper from 'soapbox/components/hover_ref_wrapper';
|
||||
import VerificationBadge from 'soapbox/components/verification_badge';
|
||||
import HoverRefWrapper from 'soapbox/components/hover-ref-wrapper';
|
||||
import VerificationBadge from 'soapbox/components/verification-badge';
|
||||
import ActionButton from 'soapbox/features/ui/components/action-button';
|
||||
import { useAppSelector, useOnScreen } from 'soapbox/hooks';
|
||||
import { getAcct } from 'soapbox/utils/accounts';
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import React from 'react';
|
||||
|
||||
import unicodeMapping from 'soapbox/features/emoji/emoji_unicode_mapping_light';
|
||||
import unicodeMapping from 'soapbox/features/emoji/emoji-unicode-mapping-light';
|
||||
import { useSettings } from 'soapbox/hooks';
|
||||
import { joinPublicPath } from 'soapbox/utils/static';
|
||||
|
||||
|
|
|
@ -2,7 +2,7 @@ import classNames from 'clsx';
|
|||
import React, { useState } from 'react';
|
||||
|
||||
import AnimatedNumber from 'soapbox/components/animated-number';
|
||||
import unicodeMapping from 'soapbox/features/emoji/emoji_unicode_mapping_light';
|
||||
import unicodeMapping from 'soapbox/features/emoji/emoji-unicode-mapping-light';
|
||||
|
||||
import Emoji from './emoji';
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@ import { useSettings } from 'soapbox/hooks';
|
|||
import Reaction from './reaction';
|
||||
|
||||
import type { List as ImmutableList, Map as ImmutableMap } from 'immutable';
|
||||
import type { Emoji } from 'soapbox/components/autosuggest_emoji';
|
||||
import type { Emoji } from 'soapbox/components/autosuggest-emoji';
|
||||
import type { AnnouncementReaction } from 'soapbox/types/entities';
|
||||
|
||||
interface IReactionsBar {
|
||||
|
|
|
@ -1,54 +0,0 @@
|
|||
import React from 'react';
|
||||
|
||||
import Icon from 'soapbox/components/icon';
|
||||
|
||||
import type { Attachment as AttachmentEntity } from 'soapbox/types/entities';
|
||||
|
||||
const filename = (url: string) => url.split('/').pop()!.split('#')[0].split('?')[0];
|
||||
|
||||
interface IAttachmentList {
|
||||
media: AttachmentEntity[],
|
||||
compact?: boolean,
|
||||
}
|
||||
|
||||
const AttachmentList: React.FC<IAttachmentList> = ({ media, compact }) => {
|
||||
if (compact) {
|
||||
return (
|
||||
<div className='attachment-list compact'>
|
||||
<ul className='attachment-list__list'>
|
||||
{media.map(attachment => {
|
||||
const displayUrl = attachment.get('remote_url') || attachment.get('url');
|
||||
|
||||
return (
|
||||
<li key={attachment.get('id')}>
|
||||
<a href={displayUrl} target='_blank' rel='noopener'><Icon id='link' /> {filename(displayUrl)}</a>
|
||||
</li>
|
||||
);
|
||||
})}
|
||||
</ul>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<div className='attachment-list'>
|
||||
<div className='attachment-list__icon'>
|
||||
<Icon id='link' />
|
||||
</div>
|
||||
|
||||
<ul className='attachment-list__list'>
|
||||
{media.map(attachment => {
|
||||
const displayUrl = attachment.get('remote_url') || attachment.get('url');
|
||||
|
||||
return (
|
||||
<li key={attachment.get('id')}>
|
||||
<a href={displayUrl} target='_blank' rel='noopener'>{filename(displayUrl)}</a>
|
||||
</li>
|
||||
);
|
||||
})}
|
||||
</ul>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
export default AttachmentList;
|
|
@ -3,13 +3,13 @@ import throttle from 'lodash/throttle';
|
|||
import React, { useState, useRef, useCallback, useEffect } from 'react';
|
||||
|
||||
import { accountSearch } from 'soapbox/actions/accounts';
|
||||
import AutosuggestInput, { AutoSuggestion } from 'soapbox/components/autosuggest_input';
|
||||
import AutosuggestInput, { AutoSuggestion } from 'soapbox/components/autosuggest-input';
|
||||
import { useAppDispatch } from 'soapbox/hooks';
|
||||
|
||||
import type { Menu } from 'soapbox/components/dropdown_menu';
|
||||
import type { Menu } from 'soapbox/components/dropdown-menu';
|
||||
import type { InputThemes } from 'soapbox/components/ui/input/input';
|
||||
|
||||
const noOp = () => {};
|
||||
const noOp = () => { };
|
||||
|
||||
interface IAutosuggestAccountInput {
|
||||
onChange: React.ChangeEventHandler<HTMLInputElement>,
|
|
@ -1,6 +1,6 @@
|
|||
import React from 'react';
|
||||
|
||||
import unicodeMapping from 'soapbox/features/emoji/emoji_unicode_mapping_light';
|
||||
import unicodeMapping from 'soapbox/features/emoji/emoji-unicode-mapping-light';
|
||||
import { joinPublicPath } from 'soapbox/utils/static';
|
||||
|
||||
export type Emoji = {
|
|
@ -1,16 +1,16 @@
|
|||
import Portal from '@reach/portal';
|
||||
import { Portal } from '@reach/portal';
|
||||
import classNames from 'clsx';
|
||||
import { List as ImmutableList } from 'immutable';
|
||||
import React from 'react';
|
||||
import ImmutablePureComponent from 'react-immutable-pure-component';
|
||||
|
||||
import AutosuggestEmoji, { Emoji } from 'soapbox/components/autosuggest_emoji';
|
||||
import AutosuggestEmoji, { Emoji } from 'soapbox/components/autosuggest-emoji';
|
||||
import Icon from 'soapbox/components/icon';
|
||||
import { Input } from 'soapbox/components/ui';
|
||||
import AutosuggestAccount from 'soapbox/features/compose/components/autosuggest_account';
|
||||
import AutosuggestAccount from 'soapbox/features/compose/components/autosuggest-account';
|
||||
import { isRtl } from 'soapbox/rtl';
|
||||
|
||||
import type { Menu, MenuItem } from 'soapbox/components/dropdown_menu';
|
||||
import type { Menu, MenuItem } from 'soapbox/components/dropdown-menu';
|
||||
import type { InputThemes } from 'soapbox/components/ui/input/input';
|
||||
|
||||
type CursorMatch = [
|
|
@ -1,13 +1,13 @@
|
|||
import Portal from '@reach/portal';
|
||||
import { Portal } from '@reach/portal';
|
||||
import classNames from 'clsx';
|
||||
import React from 'react';
|
||||
import ImmutablePureComponent from 'react-immutable-pure-component';
|
||||
import Textarea from 'react-textarea-autosize';
|
||||
|
||||
import AutosuggestAccount from '../features/compose/components/autosuggest_account';
|
||||
import AutosuggestAccount from '../features/compose/components/autosuggest-account';
|
||||
import { isRtl } from '../rtl';
|
||||
|
||||
import AutosuggestEmoji, { Emoji } from './autosuggest_emoji';
|
||||
import AutosuggestEmoji, { Emoji } from './autosuggest-emoji';
|
||||
|
||||
import type { List as ImmutableList } from 'immutable';
|
||||
|
|
@ -1,6 +1,6 @@
|
|||
import React from 'react';
|
||||
|
||||
import StillImage from 'soapbox/components/still_image';
|
||||
import StillImage from 'soapbox/components/still-image';
|
||||
|
||||
import type { Account as AccountEntity } from 'soapbox/types/entities';
|
||||
|
|
@ -1,7 +1,7 @@
|
|||
import classNames from 'clsx';
|
||||
import React from 'react';
|
||||
|
||||
import StillImage from 'soapbox/components/still_image';
|
||||
import StillImage from 'soapbox/components/still-image';
|
||||
|
||||
import type { Account } from 'soapbox/types/entities';
|
||||
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
import React, { useMemo } from 'react';
|
||||
import { defineMessages, useIntl } from 'react-intl';
|
||||
|
||||
import IconButton from 'soapbox/components/icon_button';
|
||||
import BundleContainer from 'soapbox/features/ui/containers/bundle_container';
|
||||
import IconButton from 'soapbox/components/icon-button';
|
||||
import BundleContainer from 'soapbox/features/ui/containers/bundle-container';
|
||||
import { DatePicker } from 'soapbox/features/ui/util/async-components';
|
||||
import { useAppSelector, useFeatures } from 'soapbox/hooks';
|
||||
|
|
@ -4,7 +4,7 @@ import { FormattedMessage } from 'react-intl';
|
|||
|
||||
import { fetchBirthdayReminders } from 'soapbox/actions/accounts';
|
||||
import { Widget } from 'soapbox/components/ui';
|
||||
import AccountContainer from 'soapbox/containers/account_container';
|
||||
import AccountContainer from 'soapbox/containers/account-container';
|
||||
import { useAppDispatch, useAppSelector } from 'soapbox/hooks';
|
||||
|
||||
const timeToMidnight = () => {
|
||||
|
|
|
@ -7,7 +7,7 @@ import { withRouter } from 'react-router-dom';
|
|||
// import classNames from 'clsx';
|
||||
// import { injectIntl, defineMessages } from 'react-intl';
|
||||
// import Icon from 'soapbox/components/icon';
|
||||
import SubNavigation from 'soapbox/components/sub_navigation';
|
||||
import SubNavigation from 'soapbox/components/sub-navigation';
|
||||
|
||||
// const messages = defineMessages({
|
||||
// show: { id: 'column_header.show_settings', defaultMessage: 'Show settings' },
|
|
@ -1,13 +1,13 @@
|
|||
import * as React from 'react';
|
||||
|
||||
import HoverRefWrapper from 'soapbox/components/hover_ref_wrapper';
|
||||
import HoverRefWrapper from 'soapbox/components/hover-ref-wrapper';
|
||||
import { useSoapboxConfig } from 'soapbox/hooks';
|
||||
|
||||
import { getAcct } from '../utils/accounts';
|
||||
|
||||
import Icon from './icon';
|
||||
import RelativeTimestamp from './relative-timestamp';
|
||||
import VerificationBadge from './verification_badge';
|
||||
import VerificationBadge from './verification-badge';
|
||||
|
||||
import type { Account } from 'soapbox/types/entities';
|
||||
|
||||
|
|
|
@ -2,9 +2,9 @@ import React from 'react';
|
|||
import { defineMessages, useIntl } from 'react-intl';
|
||||
import { useDispatch } from 'react-redux';
|
||||
|
||||
import { unblockDomain } from 'soapbox/actions/domain_blocks';
|
||||
import { unblockDomain } from 'soapbox/actions/domain-blocks';
|
||||
|
||||
import IconButton from './icon_button';
|
||||
import { HStack, IconButton, Text } from './ui';
|
||||
|
||||
const messages = defineMessages({
|
||||
blockDomainConfirm: { id: 'confirmations.domain_block.confirm', defaultMessage: 'Hide entire domain' },
|
||||
|
@ -34,17 +34,12 @@ const Domain: React.FC<IDomain> = ({ domain }) => {
|
|||
};
|
||||
|
||||
return (
|
||||
<div className='domain'>
|
||||
<div className='domain__wrapper'>
|
||||
<span className='domain__domain-name'>
|
||||
<strong>{domain}</strong>
|
||||
</span>
|
||||
|
||||
<div className='domain__buttons'>
|
||||
<IconButton active src={require('@tabler/icons/lock-open.svg')} title={intl.formatMessage(messages.unblockDomain, { domain })} onClick={handleDomainUnblock} />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<HStack alignItems='center' justifyContent='between' space={1} className='p-2'>
|
||||
<Text tag='span'>
|
||||
{domain}
|
||||
</Text>
|
||||
<IconButton iconClassName='h-5 w-5' src={require('@tabler/icons/lock-open.svg')} title={intl.formatMessage(messages.unblockDomain, { domain })} onClick={handleDomainUnblock} />
|
||||
</HStack>
|
||||
);
|
||||
};
|
||||
|
||||
|
|
|
@ -8,7 +8,7 @@ import { withRouter, RouteComponentProps } from 'react-router-dom';
|
|||
|
||||
import { IconButton, Counter } from 'soapbox/components/ui';
|
||||
import SvgIcon from 'soapbox/components/ui/icon/svg-icon';
|
||||
import Motion from 'soapbox/features/ui/util/optional_motion';
|
||||
import Motion from 'soapbox/features/ui/util/optional-motion';
|
||||
|
||||
import type { Status } from 'soapbox/types/entities';
|
||||
|
|
@ -3,12 +3,12 @@ import React, { useState, useEffect, useRef } from 'react';
|
|||
import { usePopper } from 'react-popper';
|
||||
import { useDispatch } from 'react-redux';
|
||||
|
||||
import { simpleEmojiReact } from 'soapbox/actions/emoji_reacts';
|
||||
import { simpleEmojiReact } from 'soapbox/actions/emoji-reacts';
|
||||
import { openModal } from 'soapbox/actions/modals';
|
||||
import EmojiSelector from 'soapbox/components/ui/emoji-selector/emoji-selector';
|
||||
import { useAppSelector, useOwnAccount, useSoapboxConfig } from 'soapbox/hooks';
|
||||
import { isUserTouching } from 'soapbox/is_mobile';
|
||||
import { getReactForStatus } from 'soapbox/utils/emoji_reacts';
|
||||
import { isUserTouching } from 'soapbox/is-mobile';
|
||||
import { getReactForStatus } from 'soapbox/utils/emoji-reacts';
|
||||
|
||||
interface IEmojiButtonWrapper {
|
||||
statusId: string,
|
||||
|
|
|
@ -3,10 +3,10 @@ import { FormattedMessage } from 'react-intl';
|
|||
import { connect } from 'react-redux';
|
||||
|
||||
import { getSoapboxConfig } from 'soapbox/actions/soapbox';
|
||||
import * as BuildConfig from 'soapbox/build_config';
|
||||
import * as BuildConfig from 'soapbox/build-config';
|
||||
import { Text, Stack } from 'soapbox/components/ui';
|
||||
import { captureException } from 'soapbox/monitoring';
|
||||
import KVStore from 'soapbox/storage/kv_store';
|
||||
import KVStore from 'soapbox/storage/kv-store';
|
||||
import sourceCode from 'soapbox/utils/code';
|
||||
import { unregisterSw } from 'soapbox/utils/sw';
|
||||
|
|
@ -0,0 +1,64 @@
|
|||
import React, { useEffect, useRef } from 'react';
|
||||
|
||||
import { isIOS } from 'soapbox/is-mobile';
|
||||
|
||||
interface IExtendedVideoPlayer {
|
||||
src: string,
|
||||
alt?: string,
|
||||
width?: number,
|
||||
height?: number,
|
||||
time?: number,
|
||||
controls?: boolean,
|
||||
muted?: boolean,
|
||||
onClick?: () => void,
|
||||
}
|
||||
|
||||
const ExtendedVideoPlayer: React.FC<IExtendedVideoPlayer> = ({ src, alt, time, controls, muted, onClick }) => {
|
||||
const video = useRef<HTMLVideoElement>(null);
|
||||
|
||||
useEffect(() => {
|
||||
const handleLoadedData = () => {
|
||||
if (time) {
|
||||
video.current!.currentTime = time;
|
||||
}
|
||||
};
|
||||
|
||||
video.current?.addEventListener('loadeddata', handleLoadedData);
|
||||
|
||||
return () => {
|
||||
video.current?.removeEventListener('loadeddata', handleLoadedData);
|
||||
};
|
||||
}, [video.current]);
|
||||
|
||||
const handleClick: React.MouseEventHandler<HTMLVideoElement> = e => {
|
||||
e.stopPropagation();
|
||||
const handler = onClick;
|
||||
if (handler) handler();
|
||||
};
|
||||
|
||||
const conditionalAttributes: React.VideoHTMLAttributes<HTMLVideoElement> = {};
|
||||
if (isIOS()) {
|
||||
conditionalAttributes.playsInline = true;
|
||||
}
|
||||
|
||||
return (
|
||||
<div className='extended-video-player'>
|
||||
<video
|
||||
ref={video}
|
||||
src={src}
|
||||
autoPlay
|
||||
role='button'
|
||||
tabIndex={0}
|
||||
aria-label={alt}
|
||||
title={alt}
|
||||
muted={muted}
|
||||
controls={controls}
|
||||
loop={!controls}
|
||||
onClick={handleClick}
|
||||
{...conditionalAttributes}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
export default ExtendedVideoPlayer;
|