Skip to content

Commit

Permalink
moved community selector from oarepo ui
Browse files Browse the repository at this point in the history
  • Loading branch information
Ducica committed Oct 22, 2024
1 parent 4eae3e6 commit 1157672
Show file tree
Hide file tree
Showing 6 changed files with 295 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import React from "react";
import { List, Header, Icon } from "semantic-ui-react";
import Overridable from "react-overridable";
import PropTypes from "prop-types";
import { Image } from "react-invenio-forms";

export const CommunityItem = ({ community, handleClick, renderLinks }) => {
const { id, title, website, logo, organizations } = community;
return (
<Overridable
id="record-community-selection-item"
community={community}
handleClick={handleClick}
renderLinks={renderLinks}
>
<List.Item
onClick={() => handleClick(id)}
className="flex align-items-center"
>
<div className="ui image community-selector-image">
<Image src={logo} size="tiny" rounded verticalAlign="top" />
</div>
<List.Content>
<Header size="small">
{renderLinks ? (
<a
onClick={(e) => {
e.stopPropagation();
}}
href={community.links.self_html}
target="_blank"
rel="noopener noreferrer"
>
{title}
</a>
) : (
title
)}
</Header>
{website && renderLinks && (
<React.Fragment>
<Icon name="linkify" />
<a
target="_blank"
rel="noopener noreferrer"
onClick={(e) => e.stopPropagation()}
href={website}
>
{website}
</a>
</React.Fragment>
)}
{organizations && (
<div>
<Icon name="building outline" />
<span>{organizations.map((o) => o.name).join(", ")}</span>
</div>
)}
</List.Content>
</List.Item>
</Overridable>
);
};

CommunityItem.propTypes = {
community: PropTypes.object.isRequired,
handleClick: PropTypes.func,
renderLinks: PropTypes.bool,
};

CommunityItem.defaultProps = {
renderLinks: true,
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
import React, { useEffect } from "react";
import PropTypes from "prop-types";
import { useFormConfig, goBack } from "@js/oarepo_ui";
import { useFormikContext, getIn } from "formik";
import { Message, Icon, Modal, List, Button } from "semantic-ui-react";
import { Trans } from "react-i18next";
import { i18next } from "@translations/oarepo_communities";
import { CommunityItem } from "./CommunityItem";

/* TODO: get actual link for the documentation */

export const GenericCommunityMessage = () => (
<Trans i18n={i18next} i18nKey="genericCommunityMessage">
You are not a member of any community. If you choose to proceed, your work
will be published in the "generic" community. We strongly recommend that you
join a community to increase the visibility of your work and to cooperate
with others more easily. You can check the available communities{" "}
<a
href="/communities"
target="_blank"
rel="noopener noreferrer"
onClick={(e) => e.stopPropagation()}
>
on our communities page.
</a>{" "}
For more details on how to join a community please refer to the instructions
on{" "}
<a
href="/documentation-url"
target="_blank"
rel="noopener noreferrer"
onClick={(e) => e.stopPropagation()}
>
how to join a community.
</a>{" "}
</Trans>
);

export const CommunitySelector = ({ fieldPath }) => {
const { values, setFieldValue } = useFormikContext();
const {
formConfig: {
allowed_communities,
preselected_community,
generic_community,
},
} = useFormConfig();
const selectedCommunity = getIn(values, "parent.communities.default", "");
useEffect(() => {
if (!values.id) {
if (preselected_community) {
setFieldValue(fieldPath, preselected_community.id);
} else if (allowed_communities.length === 1) {
setFieldValue(fieldPath, allowed_communities[0].id);
}
}
}, []);
const handleClick = (id) => {
setFieldValue(fieldPath, id);
};
return (
!values.id && (
<Modal open={!selectedCommunity}>
<Modal.Header>{i18next.t("Community selection")}</Modal.Header>
<Modal.Content>
<React.Fragment>
{allowed_communities.length > 1 && (
<React.Fragment>
<p>
{i18next.t(
"Please select community in which your work will be published:"
)}
</p>
<List selection>
{allowed_communities.map((c) => (
<CommunityItem
key={c.id}
community={c}
handleClick={handleClick}
renderLinks={false}
/>
))}
</List>
</React.Fragment>
)}
{allowed_communities.length === 0 && (
<React.Fragment>
<GenericCommunityMessage />{" "}
<span>
{i18next.t(
"If you are certain that you wish to proceed with the generic community, please click on it below."
)}
</span>
<List selection>
<CommunityItem
community={generic_community}
handleClick={handleClick}
renderLinks={false}
/>
</List>
</React.Fragment>
)}
<Message>
<Icon name="info circle" className="text size large" />
<span>
{i18next.t("All records must belong to a community.")}
</span>
</Message>
</React.Fragment>
</Modal.Content>
<Modal.Actions className="flex">
<Button
type="button"
className="ml-0"
icon
labelPosition="left"
onClick={() => goBack()}
>
<Icon name="arrow alternate circle left outline" />
{i18next.t("Go back")}
</Button>
</Modal.Actions>
</Modal>
)
);
};

CommunitySelector.propTypes = {
fieldPath: PropTypes.string,
};

CommunitySelector.defaultProps = {
fieldPath: "parent.communities.default",
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
import React from "react";
import { useFormikContext, getIn } from "formik";
import { useFormConfig } from "@js/oarepo_ui";
import PropTypes from "prop-types";
import { i18next } from "@translations/oarepo_communities";
import { Message, Icon, Button, List } from "semantic-ui-react";
import { GenericCommunityMessage } from "./CommunitySelector";
import { CommunityItem } from "./CommunityItem";
import { Trans } from "react-i18next";

export const SelectedCommunity = ({ fieldPath }) => {
const {
formConfig: {
allowed_communities,
generic_community,
preselected_community,
},
} = useFormConfig();
const { values, setFieldValue } = useFormikContext();
const selectedCommunityId = getIn(values, fieldPath, "");
let selectedCommunity = allowed_communities.find(
(c) => c.id === selectedCommunityId
);
const isGeneric = generic_community.id === selectedCommunityId;
if (isGeneric) {
selectedCommunity = generic_community;
}
const handleCommunityRemoval = () => {
setFieldValue(fieldPath, "");
};
return (
<React.Fragment>
{values?.id && (
<p>
{i18next.t(
"Your record will be published in the following community:"
)}
</p>
)}
{!values?.id &&
allowed_communities.length > 1 &&
!preselected_community && (
<Trans i18n={i18next}>
Your work will be saved in the following community. Please note that
after saving it will not be possible to transfer it to another
community. Click
<Button
className="ml-5 mr-5"
onClick={handleCommunityRemoval}
size="mini"
>
here
</Button>
to change the selection.
</Trans>
)}
{selectedCommunity && (
<List>
<CommunityItem community={selectedCommunity} />
</List>
)}
{isGeneric ? (
<Message>
<Icon name="warning circle" className="text size large" />
<GenericCommunityMessage />
</Message>
) : null}
</React.Fragment>
);
};

SelectedCommunity.propTypes = {
fieldPath: PropTypes.string,
};

SelectedCommunity.defaultProps = {
fieldPath: "parent.communities.default",
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export * from "./SelectedCommunity.jsx";
export * from "./CommunitySelector.jsx";
export * from "./CommunityItem.jsx";
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
export * from "./CommunityInvitationsModal";
export * from "./CommunitySelector";
Original file line number Diff line number Diff line change
Expand Up @@ -29,3 +29,9 @@
object-fit: contain;
}
}

.ui.image.community-selector-image img {
max-height: 80px;
min-width: 80px;
object-fit: contain;
}

0 comments on commit 1157672

Please sign in to comment.