Creates item-metadata and item-metadatum blocks. #566.
This commit is contained in:
parent
7f7deab0be
commit
c2ca3a3437
|
@ -0,0 +1,69 @@
|
|||
{
|
||||
"$schema": "https://schemas.wp.org/trunk/block.json",
|
||||
"name": "tainacan/item-metadata",
|
||||
"title": "Tainacan Item Metadata",
|
||||
"apiVersion": 2,
|
||||
"category": "tainacan-blocks",
|
||||
"keywords": [ "item", "metadata", "fields", "values" ],
|
||||
"description": "The item metadata, including a label and its value.",
|
||||
"textdomain": "tainacan",
|
||||
"example": {
|
||||
"attributes": {
|
||||
"content": "preview"
|
||||
}
|
||||
},
|
||||
"attributes": {
|
||||
"content": {
|
||||
"type": "array",
|
||||
"source": "query",
|
||||
"selector": "div"
|
||||
},
|
||||
"collectionId": {
|
||||
"type": "string",
|
||||
"default": ""
|
||||
},
|
||||
"itemId": {
|
||||
"type": "string",
|
||||
"default": ""
|
||||
},
|
||||
"isModalOpen": {
|
||||
"type": "boolean",
|
||||
"default": false
|
||||
},
|
||||
"isLoading": {
|
||||
"type": "boolean",
|
||||
"default": false
|
||||
},
|
||||
"itemRequestSource": {
|
||||
"type": "string",
|
||||
"default": ""
|
||||
},
|
||||
"itemMetadata": {
|
||||
"type": "array",
|
||||
"default": []
|
||||
},
|
||||
"itemMetadataTemplate": {
|
||||
"type": "array",
|
||||
"default": []
|
||||
}
|
||||
},
|
||||
"providesContext": {
|
||||
"tainacan/itemId": "itemId",
|
||||
"tainacan/collectionId": "collectionId"
|
||||
},
|
||||
"supports": {
|
||||
"align": ["full", "wide"],
|
||||
"multiple": true,
|
||||
"color": {
|
||||
"text": true,
|
||||
"background": true,
|
||||
"gradients": true,
|
||||
"link": true
|
||||
},
|
||||
"spacing": {
|
||||
"padding": true
|
||||
}
|
||||
},
|
||||
"editorScript": "item-metadata",
|
||||
"editorStyle": "item-metadata"
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
export default [];
|
|
@ -0,0 +1,165 @@
|
|||
const { __ } = wp.i18n;
|
||||
|
||||
const { Button, Spinner, Placeholder } = wp.components;
|
||||
|
||||
const { useBlockProps, InnerBlocks } = (tainacan_blocks.wp_version < '5.2' ? wp.editor : wp.blockEditor );
|
||||
|
||||
import SingleItemModal from '../../js/selection/single-item-modal.js';
|
||||
import tainacan from '../../js/axios.js';
|
||||
import axios from 'axios';
|
||||
|
||||
export default function ({ attributes, setAttributes, className, isSelected, clientId }) {
|
||||
|
||||
let {
|
||||
content,
|
||||
collectionId,
|
||||
itemId,
|
||||
isLoading,
|
||||
itemRequestSource,
|
||||
isModalOpen,
|
||||
itemMetadata,
|
||||
itemMetadataTemplate
|
||||
} = attributes;
|
||||
|
||||
// Gets blocks props from hook
|
||||
const blockProps = tainacan_blocks.wp_version < '5.6' ? { className: className } : useBlockProps();
|
||||
|
||||
function setContent() {
|
||||
isLoading = true;
|
||||
|
||||
setAttributes({
|
||||
isLoading: isLoading
|
||||
});
|
||||
|
||||
if (itemRequestSource != undefined && typeof itemRequestSource == 'function')
|
||||
itemRequestSource.cancel('Previous items search canceled.');
|
||||
|
||||
itemRequestSource = axios.CancelToken.source();
|
||||
|
||||
let endpoint = '/item/'+ itemId + '/metadata';
|
||||
|
||||
tainacan.get(endpoint, { cancelToken: itemRequestSource.token })
|
||||
.then(response => {
|
||||
|
||||
itemMetadata = response.data ? response.data : [];
|
||||
setAttributes({
|
||||
itemMetadata: itemMetadata,
|
||||
isLoading: false,
|
||||
itemRequestSource: itemRequestSource
|
||||
});
|
||||
getItemMetadataTemplates();
|
||||
});
|
||||
}
|
||||
|
||||
function getItemMetadataTemplates() {
|
||||
itemMetadataTemplate = [];
|
||||
|
||||
itemMetadata.forEach((itemMetadatum) => {
|
||||
|
||||
if (itemMetadatum.value && itemMetadatum.metadatum && itemMetadatum.metadatum.id) {
|
||||
itemMetadataTemplate.push([
|
||||
'tainacan/item-metadatum',
|
||||
{
|
||||
placeholder: __( 'Item Metadatum', 'tainacan' ),
|
||||
metadatumId: itemMetadatum.metadatum.id,
|
||||
itemId: itemId,
|
||||
collectionId: collectionId
|
||||
}
|
||||
]);
|
||||
}
|
||||
});
|
||||
setAttributes({ itemMetadataTemplate: itemMetadataTemplate });
|
||||
}
|
||||
|
||||
return content == 'preview' ?
|
||||
<div className={className}>
|
||||
<img
|
||||
width="100%"
|
||||
src={ `${tainacan_blocks.base_url}/assets/images/related-carousel-items.png` } />
|
||||
</div>
|
||||
: (
|
||||
<div { ...blockProps }>
|
||||
|
||||
{ isSelected ?
|
||||
(
|
||||
<div>
|
||||
{ isModalOpen ?
|
||||
<SingleItemModal
|
||||
modalTitle={ __('Select one item to render its metadata', 'tainacan') }
|
||||
applyButtonLabel={ __('List metadata for this item', 'tainacan') }
|
||||
existingCollectionId={ collectionId }
|
||||
existingItemId={ itemId }
|
||||
onSelectCollection={ (selectedCollectionId) => {
|
||||
collectionId = selectedCollectionId;
|
||||
setAttributes({
|
||||
collectionId: collectionId
|
||||
});
|
||||
}}
|
||||
onApplySelectedItem={ (selectedItemId) => {
|
||||
itemId = selectedItemId;
|
||||
setAttributes({
|
||||
itemId: itemId,
|
||||
isModalOpen: false
|
||||
});
|
||||
setContent();
|
||||
}}
|
||||
onCancelSelection={ () => setAttributes({ isModalOpen: false }) }/>
|
||||
: null
|
||||
}
|
||||
|
||||
</div>
|
||||
) : null
|
||||
}
|
||||
|
||||
{ !itemId ? (
|
||||
<Placeholder
|
||||
className="tainacan-block-placeholder"
|
||||
icon={(
|
||||
<img
|
||||
width={148}
|
||||
src={ `${tainacan_blocks.base_url}/assets/images/tainacan_logo_header.svg` }
|
||||
alt="Tainacan Logo"/>
|
||||
)}>
|
||||
<p>
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
viewBox="0 0 24 24"
|
||||
height="24px"
|
||||
width="24px">
|
||||
<path d="M16,6H12a2,2,0,0,0-2,2v6.52A6,6,0,0,1,12,19a6,6,0,0,1-.73,2.88A1.92,1.92,0,0,0,12,22h8a2,2,0,0,0,2-2V12Zm-1,6V7.5L19.51,12ZM15,2V4H8v9.33A5.8,5.8,0,0,0,6,13V4A2,2,0,0,1,8,2ZM10.09,19.05,7,22.11V16.05L8,17l2,2ZM5,16.05v6.06L2,19.11Z"/>
|
||||
</svg>
|
||||
{__('Select an item to display its metadata list.', 'tainacan')}
|
||||
</p>
|
||||
<Button
|
||||
isPrimary
|
||||
type="button"
|
||||
onClick={ () => {
|
||||
isModalOpen = true;
|
||||
setAttributes( {
|
||||
isModalOpen: isModalOpen
|
||||
});
|
||||
}
|
||||
}>
|
||||
{__('Select Item', 'tainacan')}
|
||||
</Button>
|
||||
</Placeholder>
|
||||
) : null
|
||||
}
|
||||
|
||||
{ isLoading ?
|
||||
<div class="spinner-container">
|
||||
<Spinner />
|
||||
</div> :
|
||||
<div className={ 'item-metadata-edit-container' }>
|
||||
{ itemMetadata.length ?
|
||||
<InnerBlocks
|
||||
allowedBlocks={ true }
|
||||
template={ itemMetadataTemplate } />
|
||||
: null
|
||||
}
|
||||
</div>
|
||||
}
|
||||
|
||||
</div>
|
||||
);
|
||||
};
|
|
@ -0,0 +1,14 @@
|
|||
const { SVG, Path } = wp.components;
|
||||
|
||||
export default (
|
||||
<SVG
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
viewBox="-1 -1 26 26"
|
||||
height="24px"
|
||||
width="24px">
|
||||
<Path
|
||||
d="M 7.5947245,4.2973622 H 16.405277 V 19.702638 H 7.5947245 Z M 18.594724,7.5947241 H 23 V 16.405276 H 18.594724 Z M 1.0000002,16.405276 V 7.5947241 H 5.405276 v 8.8105519 z"
|
||||
/>
|
||||
</SVG>
|
||||
);
|
||||
|
|
@ -0,0 +1,15 @@
|
|||
import tainacanRegisterBlockType from '../../js/compatibility/tainacan-blocks-compat-register.js';
|
||||
|
||||
import metadata from './block.json';
|
||||
import icon from './icon.js';
|
||||
import edit from './edit.js';
|
||||
import save from './save.js';
|
||||
import deprecated from './deprecated.js';
|
||||
|
||||
tainacanRegisterBlockType({
|
||||
metadata,
|
||||
icon,
|
||||
edit,
|
||||
save,
|
||||
deprecated
|
||||
});
|
|
@ -0,0 +1,7 @@
|
|||
const { useBlockProps, InnerBlocks } = (tainacan_blocks.wp_version < '5.2' ? wp.editor : wp.blockEditor );
|
||||
|
||||
export default function({ className }) {
|
||||
const blockProps = tainacan_blocks.wp_version < '5.6' ? { className: className } : useBlockProps.save();
|
||||
|
||||
return <div data-module="item-metadata" { ...blockProps }><InnerBlocks.Content /></div>
|
||||
};
|
|
@ -0,0 +1,61 @@
|
|||
{
|
||||
"$schema": "https://schemas.wp.org/trunk/block.json",
|
||||
"name": "tainacan/item-metadatum",
|
||||
"title": "Tainacan Item metadatum",
|
||||
"apiVersion": 2,
|
||||
"category": "tainacan-blocks",
|
||||
"keywords": [ "item", "metadatum", "field", "value" ],
|
||||
"description": "A single item metadatum, including a label and its value.",
|
||||
"textdomain": "tainacan",
|
||||
"example": {
|
||||
"attributes": {
|
||||
"content": "preview"
|
||||
}
|
||||
},
|
||||
"attributes": {
|
||||
"content": {
|
||||
"type": "array",
|
||||
"source": "query",
|
||||
"selector": "div"
|
||||
},
|
||||
"collectionId": {
|
||||
"type": "integer",
|
||||
"default": ""
|
||||
},
|
||||
"itemId": {
|
||||
"type": "integer",
|
||||
"default": ""
|
||||
},
|
||||
"metadatumId": {
|
||||
"type": "integer",
|
||||
"default": ""
|
||||
},
|
||||
"metadatumType": {
|
||||
"type": "string",
|
||||
"default": ""
|
||||
},
|
||||
"isModalOpen": {
|
||||
"type": "boolean",
|
||||
"default": false
|
||||
}
|
||||
},
|
||||
"usesContext": [
|
||||
"tainacan/itemId",
|
||||
"tainacan/collectionId"
|
||||
],
|
||||
"supports": {
|
||||
"align": ["full", "wide"],
|
||||
"multiple": true,
|
||||
"color": {
|
||||
"text": true,
|
||||
"background": true,
|
||||
"gradients": true,
|
||||
"link": true
|
||||
},
|
||||
"spacing": {
|
||||
"padding": true
|
||||
}
|
||||
},
|
||||
"editorScript": "item-metadatum",
|
||||
"editorStyle": "item-metadatum"
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
export default [];
|
|
@ -0,0 +1,121 @@
|
|||
const { __ } = wp.i18n;
|
||||
|
||||
const { Button, Placeholder } = wp.components;
|
||||
|
||||
const ServerSideRender = wp.serverSideRender;
|
||||
const { useBlockProps } = (tainacan_blocks.wp_version < '5.2' ? wp.editor : wp.blockEditor );
|
||||
|
||||
import SingleItemMetadatumModal from '../../js/selection/single-item-metadatum-modal.js';
|
||||
|
||||
export default function ({ attributes, setAttributes, className, isSelected }) {
|
||||
|
||||
let {
|
||||
content,
|
||||
collectionId,
|
||||
itemId,
|
||||
metadatumId,
|
||||
metadatumType,
|
||||
isModalOpen,
|
||||
} = attributes;
|
||||
|
||||
// Gets blocks props from hook
|
||||
const blockProps = tainacan_blocks.wp_version < '5.6' ? { className: className } : useBlockProps();
|
||||
const currentWPVersion = (typeof tainacan_blocks != 'undefined') ? tainacan_blocks.wp_version : tainacan_plugin.wp_version;
|
||||
|
||||
return content == 'preview' ?
|
||||
<div className={className}>
|
||||
<img
|
||||
width="100%"
|
||||
src={ `${tainacan_blocks.base_url}/assets/images/related-carousel-items.png` } />
|
||||
</div>
|
||||
: (
|
||||
<div { ...blockProps }>
|
||||
|
||||
{ isSelected ?
|
||||
(
|
||||
<div>
|
||||
{ isModalOpen ?
|
||||
<SingleItemMetadatumModal
|
||||
modalTitle={ __('Select one item to render its metadata', 'tainacan') }
|
||||
existingCollectionId={ collectionId }
|
||||
existingItemId={ itemId }
|
||||
existingMetadatumId={ metadatumId }
|
||||
onSelectCollection={ (selectedCollectionId) => {
|
||||
collectionId = selectedCollectionId;
|
||||
setAttributes({
|
||||
collectionId: collectionId
|
||||
});
|
||||
}}
|
||||
onSelectItem={ (selectedItemId) => {
|
||||
itemId = selectedItemId;
|
||||
setAttributes({
|
||||
itemId: itemId
|
||||
});
|
||||
}}
|
||||
onApplySelectedMetadatum={ (selectedMetadatum) => {
|
||||
metadatumId = selectedMetadatum.metadatumId;
|
||||
metadatumType = selectedMetadatum.metadatumType;
|
||||
|
||||
setAttributes({
|
||||
metadatumId: metadatumId,
|
||||
metadatumType: metadatumType,
|
||||
isModalOpen: false
|
||||
});
|
||||
}}
|
||||
onCancelSelection={ () => setAttributes({ isModalOpen: false }) }/>
|
||||
: null
|
||||
}
|
||||
|
||||
</div>
|
||||
) : null
|
||||
}
|
||||
|
||||
{ !(collectionId && itemId && metadatumId) ? (
|
||||
<Placeholder
|
||||
className="tainacan-block-placeholder"
|
||||
icon={(
|
||||
<img
|
||||
width={148}
|
||||
src={ `${tainacan_blocks.base_url}/assets/images/tainacan_logo_header.svg` }
|
||||
alt="Tainacan Logo"/>
|
||||
)}>
|
||||
<p>
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
viewBox="0 0 24 24"
|
||||
height="24px"
|
||||
width="24px">
|
||||
<path d="M16,6H12a2,2,0,0,0-2,2v6.52A6,6,0,0,1,12,19a6,6,0,0,1-.73,2.88A1.92,1.92,0,0,0,12,22h8a2,2,0,0,0,2-2V12Zm-1,6V7.5L19.51,12ZM15,2V4H8v9.33A5.8,5.8,0,0,0,6,13V4A2,2,0,0,1,8,2ZM10.09,19.05,7,22.11V16.05L8,17l2,2ZM5,16.05v6.06L2,19.11Z"/>
|
||||
</svg>
|
||||
{__('Select an item metadata to display its label and value.', 'tainacan')}
|
||||
</p>
|
||||
<Button
|
||||
isPrimary
|
||||
type="button"
|
||||
onClick={ () => {
|
||||
isModalOpen = true;
|
||||
setAttributes( {
|
||||
isModalOpen: isModalOpen
|
||||
});
|
||||
}
|
||||
}>
|
||||
{__('Select Item Metadatum', 'tainacan')}
|
||||
</Button>
|
||||
</Placeholder>
|
||||
) : null
|
||||
}
|
||||
|
||||
{ (collectionId && itemId && metadatumId) ? (
|
||||
<div className={ 'item-metadatum-edit-container' }>
|
||||
<ServerSideRender
|
||||
block="tainacan/item-metadatum"
|
||||
attributes={ attributes }
|
||||
httpMethod={ currentWPVersion >= '5.5' ? 'POST' : 'GET' }
|
||||
/>
|
||||
</div>
|
||||
) : null
|
||||
}
|
||||
|
||||
</div>
|
||||
);
|
||||
};
|
|
@ -0,0 +1,14 @@
|
|||
const { SVG, Path } = wp.components;
|
||||
|
||||
export default (
|
||||
<SVG
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
viewBox="-1 -1 26 26"
|
||||
height="24px"
|
||||
width="24px">
|
||||
<Path
|
||||
d="M 7.5947245,4.2973622 H 16.405277 V 19.702638 H 7.5947245 Z M 18.594724,7.5947241 H 23 V 16.405276 H 18.594724 Z M 1.0000002,16.405276 V 7.5947241 H 5.405276 v 8.8105519 z"
|
||||
/>
|
||||
</SVG>
|
||||
);
|
||||
|
|
@ -0,0 +1,15 @@
|
|||
import tainacanRegisterBlockType from '../../js/compatibility/tainacan-blocks-compat-register.js';
|
||||
|
||||
import metadata from './block.json';
|
||||
import icon from './icon.js';
|
||||
import edit from './edit.js';
|
||||
import save from './save.js';
|
||||
import deprecated from './deprecated.js';
|
||||
|
||||
tainacanRegisterBlockType({
|
||||
metadata,
|
||||
icon,
|
||||
edit,
|
||||
save,
|
||||
deprecated
|
||||
});
|
|
@ -0,0 +1,3 @@
|
|||
export default function() {
|
||||
return null
|
||||
};
|
|
@ -0,0 +1,29 @@
|
|||
<?php
|
||||
|
||||
/**
|
||||
* Renders the content of the item metadata block
|
||||
* using Tainacan template functions
|
||||
*/
|
||||
function tainacan_blocks_render_item_metadatum( $block_attributes, $content, $block ) {
|
||||
|
||||
$item_id = !empty($block->context['tainacan/itemId']) ? $block->context['tainacan/itemId'] : (isset($block_attributes['itemId']) ? $block_attributes['itemId'] : false);
|
||||
$metadatum_id = isset($block_attributes['metadatumId']) ? $block_attributes['metadatumId'] : false;
|
||||
|
||||
if ( !$item_id || !$metadatum_id )
|
||||
return '';
|
||||
|
||||
$wrapper_attributes = get_block_wrapper_attributes(
|
||||
array(
|
||||
'class' => 'metadata-type-$type'
|
||||
)
|
||||
);
|
||||
|
||||
return tainacan_get_the_metadata(
|
||||
array(
|
||||
'metadata' => $metadatum_id,
|
||||
'before' => '<div ' . $wrapper_attributes . '>',
|
||||
'after' => '</div>'
|
||||
),
|
||||
$item_id
|
||||
);
|
||||
}
|
|
@ -16,7 +16,9 @@ const TAINACAN_BLOCKS = [
|
|||
'terms-list' => [],
|
||||
'faceted-search' => [],
|
||||
'item-submission-form' => [],
|
||||
'item-gallery' => ['render_callback' => 'tainacan_blocks_render_items_gallery']
|
||||
'item-gallery' => ['render_callback' => 'tainacan_blocks_render_items_gallery'],
|
||||
'item-metadata' => [],
|
||||
'item-metadatum' => ['render_callback' => 'tainacan_blocks_render_item_metadatum']
|
||||
];
|
||||
|
||||
// Lets do this!
|
||||
|
|
|
@ -0,0 +1,495 @@
|
|||
import tainacan from '../axios.js';
|
||||
import axios from 'axios';
|
||||
|
||||
const { __ } = wp.i18n;
|
||||
|
||||
const { TextControl, Button, Modal, RadioControl, SelectControl, Spinner } = wp.components;
|
||||
const currentWPVersion = (typeof tainacan_blocks != 'undefined') ? tainacan_blocks.wp_version : tainacan_plugin.wp_version;
|
||||
|
||||
export default class SingleItemModal extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
|
||||
// Initialize state
|
||||
this.state = {
|
||||
collectionsPerPage: 24,
|
||||
collectionId: undefined,
|
||||
itemId: undefined,
|
||||
metadatumId: undefined,
|
||||
collectionName: '',
|
||||
isLoadingCollections: false,
|
||||
modalCollections: [],
|
||||
itemTitle: '',
|
||||
metadatumType: undefined,
|
||||
isLoadingMetadata: false,
|
||||
modalMetadata: [],
|
||||
totalModalCollections: 0,
|
||||
collectionOrderBy: 'date-desc',
|
||||
collectionPage: 1,
|
||||
temporaryCollectionId: '',
|
||||
temporaryItemId: '',
|
||||
temporaryMetadatumId: '',
|
||||
searchCollectionName: '',
|
||||
collections: [],
|
||||
collectionsRequestSource: undefined,
|
||||
metadata: [],
|
||||
metadataRequestSource: undefined,
|
||||
searchURL: '',
|
||||
itemsPerPage: 12
|
||||
};
|
||||
|
||||
// Bind events
|
||||
this.resetCollections = this.resetCollections.bind(this);
|
||||
this.selectCollection = this.selectCollection.bind(this);
|
||||
this.fetchCollections = this.fetchCollections.bind(this);
|
||||
this.fetchModalCollections = this.fetchModalCollections.bind(this);
|
||||
this.fetchCollection = this.fetchCollection.bind(this);
|
||||
|
||||
this.fetchItem = this.fetchItem.bind(this);
|
||||
this.selectItem = this.selectItem.bind(this);
|
||||
|
||||
this.fetchModalMetadata = this.fetchModalMetadata.bind(this);
|
||||
|
||||
this.applySelectedMetadatum = this.applySelectedMetadatum.bind(this);
|
||||
}
|
||||
|
||||
componentWillMount() {
|
||||
|
||||
this.setState({
|
||||
collectionId: this.props.existingCollectionId,
|
||||
itemId: this.props.existingItemId,
|
||||
metadatumId: this.props.existingMetadatumId
|
||||
});
|
||||
|
||||
if (this.props.existingCollectionId) {
|
||||
this.fetchCollection(this.props.existingCollectionId);
|
||||
this.setState({
|
||||
searchURL: tainacan_blocks.admin_url + 'admin.php?itemsSingleSelectionMode=true&page=tainacan_admin#/collections/'+ this.props.existingCollectionId + '/items/?status=publish'
|
||||
});
|
||||
|
||||
if (this.props.existingItemId) {
|
||||
this.fetchItem(this.props.existingItemId);
|
||||
this.fetchModalMetadata();
|
||||
}
|
||||
|
||||
} else {
|
||||
this.setState({ collectionPage: 1 });
|
||||
this.fetchModalCollections();
|
||||
}
|
||||
}
|
||||
|
||||
// COLLECTIONS RELATED --------------------------------------------------
|
||||
fetchModalCollections() {
|
||||
|
||||
let someModalCollections = this.state.modalCollections;
|
||||
if (this.state.collectionPage <= 1)
|
||||
someModalCollections = [];
|
||||
|
||||
let endpoint = '/collections/?perpage=' + this.state.collectionsPerPage + '&paged=' + this.state.collectionPage;
|
||||
|
||||
if (this.state.collectionOrderBy == 'date')
|
||||
endpoint += '&orderby=date&order=asc';
|
||||
else if (this.state.collectionOrderBy == 'date-desc')
|
||||
endpoint += '&orderby=date&order=desc';
|
||||
else if (this.state.collectionOrderBy == 'title')
|
||||
endpoint += '&orderby=title&order=asc';
|
||||
else if (this.state.collectionOrderBy == 'title-desc')
|
||||
endpoint += '&orderby=title&order=desc';
|
||||
|
||||
this.setState({
|
||||
isLoadingCollections: true,
|
||||
collectionPage: this.state.collectionPage + 1,
|
||||
modalCollections: someModalCollections
|
||||
});
|
||||
|
||||
tainacan.get(endpoint)
|
||||
.then(response => {
|
||||
|
||||
let otherModalCollections = this.state.modalCollections;
|
||||
for (let collection of response.data) {
|
||||
otherModalCollections.push({
|
||||
name: collection.name,
|
||||
id: collection.id
|
||||
});
|
||||
}
|
||||
|
||||
this.setState({
|
||||
isLoadingCollections: false,
|
||||
modalCollections: otherModalCollections,
|
||||
totalModalCollections: response.headers['x-wp-total']
|
||||
});
|
||||
|
||||
return otherModalCollections;
|
||||
})
|
||||
.catch(error => {
|
||||
console.log('Error trying to fetch collections: ' + error);
|
||||
});
|
||||
}
|
||||
|
||||
fetchCollection(collectionId) {
|
||||
tainacan.get('/collections/' + collectionId)
|
||||
.then((response) => {
|
||||
this.setState({ collectionName: response.data.name });
|
||||
}).catch(error => {
|
||||
console.log('Error trying to fetch collection: ' + error);
|
||||
});
|
||||
}
|
||||
|
||||
fetchItem(itemId) {
|
||||
tainacan.get('/collections/' + this.state.collectionId + '/items/' + itemId)
|
||||
.then((response) => {
|
||||
this.setState({ itemTitle: response.data.title });
|
||||
}).catch(error => {
|
||||
console.log('Error trying to fetch collection: ' + error);
|
||||
});
|
||||
}
|
||||
|
||||
selectCollection(selectedCollectionId) {
|
||||
this.setState({
|
||||
collectionId: selectedCollectionId,
|
||||
searchURL: tainacan_blocks.admin_url + 'admin.php?itemsSingleSelectionMode=true&page=tainacan_admin#/collections/' + selectedCollectionId + '/items/?status=publish'
|
||||
});
|
||||
|
||||
this.props.onSelectCollection(selectedCollectionId);
|
||||
this.fetchCollection(selectedCollectionId);
|
||||
}
|
||||
|
||||
fetchCollections(name) {
|
||||
|
||||
if (this.state.collectionsRequestSource != undefined)
|
||||
this.state.collectionsRequestSource.cancel('Previous collections search canceled.');
|
||||
|
||||
let aCollectionRequestSource = axios.CancelToken.source();
|
||||
|
||||
this.setState({
|
||||
collectionsRequestSource: aCollectionRequestSource,
|
||||
isLoadingCollections: true,
|
||||
collections: [],
|
||||
items: []
|
||||
});
|
||||
|
||||
let endpoint = '/collections/?perpage=' + this.state.collectionsPerPage;
|
||||
if (name != undefined && name != '')
|
||||
endpoint += '&search=' + name;
|
||||
|
||||
if (this.state.collectionOrderBy == 'date')
|
||||
endpoint += '&orderby=date&order=asc';
|
||||
else if (this.state.collectionOrderBy == 'date-desc')
|
||||
endpoint += '&orderby=date&order=desc';
|
||||
else if (this.state.collectionOrderBy == 'title')
|
||||
endpoint += '&orderby=title&order=asc';
|
||||
else if (this.state.collectionOrderBy == 'title-desc')
|
||||
endpoint += '&orderby=title&order=desc';
|
||||
|
||||
tainacan.get(endpoint, { cancelToken: aCollectionRequestSource.token })
|
||||
.then(response => {
|
||||
let someCollections = response.data.map((collection) => ({ name: collection.name, id: collection.id + '' }));
|
||||
|
||||
this.setState({
|
||||
isLoadingCollections: false,
|
||||
collections: someCollections
|
||||
});
|
||||
|
||||
return someCollections;
|
||||
})
|
||||
.catch(error => {
|
||||
console.log('Error trying to fetch collections: ' + error);
|
||||
});
|
||||
}
|
||||
|
||||
fetchModalMetadata() {
|
||||
|
||||
let someModalMetadata = [];
|
||||
let endpoint = '/collection/' + this.state.collectionId + '/metadata/?nopaging=1';
|
||||
|
||||
this.setState({
|
||||
isLoadingMetadata: true,
|
||||
modalMetadata: someModalMetadata
|
||||
});
|
||||
|
||||
tainacan.get(endpoint)
|
||||
.then(response => {
|
||||
|
||||
let otherModalMetadata = this.state.modalMetadata;
|
||||
|
||||
for (let metadatum of response.data) {
|
||||
otherModalMetadata.push({
|
||||
name: metadatum.name,
|
||||
id: metadatum.id,
|
||||
type: metadatum.metadata_type,
|
||||
typeLabel: metadatum.metadata_type_object ? metadatum.metadata_type_object.name : ''
|
||||
});
|
||||
}
|
||||
|
||||
this.setState({
|
||||
isLoadingMetadata: false,
|
||||
modalMetadata: otherModalMetadata
|
||||
});
|
||||
|
||||
return otherModalMetadata;
|
||||
})
|
||||
.catch(error => {
|
||||
console.log('Error trying to fetch metadata: ' + error);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
selectItem() {
|
||||
let iframe = document.getElementById("itemsFrame");
|
||||
if (iframe) {
|
||||
let params = new URLSearchParams(iframe.contentWindow.location.search);
|
||||
let selectedItems = params.getAll('selecteditems');
|
||||
params.delete('selecteditems')
|
||||
if (selectedItems[0]) {
|
||||
this.setState({
|
||||
itemId: selectedItems[0]
|
||||
});
|
||||
this.props.onSelectItem(selectedItems[0]);
|
||||
this.fetchModalMetadata();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
applySelectedMetadatum(selectedMetadatum) {
|
||||
this.setState({
|
||||
metadatumId: selectedMetadatum.id,
|
||||
metadatumType: selectedMetadatum.type
|
||||
});
|
||||
this.props.onApplySelectedMetadatum({
|
||||
metadatumId: selectedMetadatum.id,
|
||||
metadatumType: selectedMetadatum.type
|
||||
});
|
||||
}
|
||||
|
||||
resetCollections() {
|
||||
|
||||
this.setState({
|
||||
collectionId: null,
|
||||
collectionPage: 1,
|
||||
modalCollections: []
|
||||
});
|
||||
this.fetchModalCollections();
|
||||
}
|
||||
|
||||
resetItem() {
|
||||
|
||||
this.setState({
|
||||
itemId: null,
|
||||
});
|
||||
}
|
||||
|
||||
cancelSelection() {
|
||||
|
||||
this.setState({
|
||||
modalCollections: [],
|
||||
modalMetadata: []
|
||||
});
|
||||
|
||||
this.props.onCancelSelection();
|
||||
}
|
||||
|
||||
render() {
|
||||
return (this.state.collectionId && this.state.itemId) ? (
|
||||
// Metadata modal
|
||||
<Modal
|
||||
className="wp-block-tainacan-modal"
|
||||
title={__('Select a metadatum to show it\'s value', 'tainacan')}
|
||||
onRequestClose={ () => this.cancelSelection() }
|
||||
contentLabel={__('Select metadatum', 'tainacan')}>
|
||||
{(
|
||||
this.state.modalMetadata.length > 0 ?
|
||||
(
|
||||
<div>
|
||||
<div className="modal-radio-list">
|
||||
<RadioControl
|
||||
selected={ this.state.temporaryMetadatumId }
|
||||
options={
|
||||
this.state.modalMetadata.map((metadatum) => {
|
||||
return { label: metadatum.name + ' (' + metadatum.typeLabel + ')', value: '' + metadatum.id }
|
||||
})
|
||||
}
|
||||
onChange={ ( aMetadatumId ) => {
|
||||
this.setState({
|
||||
temporaryMetadatumId: aMetadatumId
|
||||
});
|
||||
} } />
|
||||
</div>
|
||||
<br/>
|
||||
</div>
|
||||
) : this.state.isLoadingMetadata ? <Spinner/> :
|
||||
<div className="modal-loadmore-section">
|
||||
<p>{ __('Sorry, no metadatum found.', 'tainacan') }</p>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
<div className="modal-footer-area">
|
||||
<Button
|
||||
isSecondary
|
||||
onClick={ () => { this.resetCollections(); }}>
|
||||
{__('Switch Collection', 'tainacan')}
|
||||
</Button>
|
||||
<Button
|
||||
isSecondary
|
||||
onClick={ () => { this.resetItem(); }}>
|
||||
{__('Switch Item', 'tainacan')}
|
||||
</Button>
|
||||
<Button
|
||||
isPrimary
|
||||
disabled={ this.state.temporaryMetadatumId == undefined || this.state.temporaryMetadatumId == null || this.state.temporaryMetadatumId == ''}
|
||||
onClick={ () => { this.applySelectedMetadatum(this.state.modalMetadata.find((metadatatum) => metadatatum.id == this.state.temporaryMetadatumId)); } }>
|
||||
{__('Use this metadatum', 'tainacan')}
|
||||
</Button>
|
||||
</div>
|
||||
</Modal>
|
||||
|
||||
) : (
|
||||
this.state.collectionId ? (
|
||||
// Item modal
|
||||
<Modal
|
||||
className={ 'wp-block-tainacan-modal dynamic-modal ' + (currentWPVersion < 5.9 ? 'wp-version-smaller-than-5-9' : '') }
|
||||
title={ this.props.modalTitle ? this.props.modalTitle : __('Select one item for the block', 'tainacan') }
|
||||
onRequestClose={ () => this.cancelSelection() }
|
||||
shouldCloseOnClickOutside={ false }
|
||||
contentLabel={ this.props.modalTitle ? this.props.modalTitle : __('Select one item for the block', 'tainacan') }>
|
||||
<iframe
|
||||
id="itemsFrame"
|
||||
src={ this.state.searchURL } />
|
||||
<div className="modal-footer-area">
|
||||
<Button
|
||||
isSecondary
|
||||
onClick={ () => { this.resetCollections() }}>
|
||||
{__('Switch collection', 'tainacan')}
|
||||
</Button>
|
||||
<Button
|
||||
style={{ marginLeft: 'auto' }}
|
||||
isPrimary
|
||||
onClick={ () => this.selectItem() }>
|
||||
{ __('Use this item', 'tainacan') }
|
||||
</Button>
|
||||
</div>
|
||||
</Modal>
|
||||
) : (
|
||||
// Collections modal
|
||||
<Modal
|
||||
className="wp-block-tainacan-modal"
|
||||
title={__('Select a collection to fetch items from', 'tainacan')}
|
||||
onRequestClose={ () => this.cancelSelection() }
|
||||
shouldCloseOnClickOutside={ false }
|
||||
contentLabel={__('Select item', 'tainacan')}>
|
||||
<div>
|
||||
<div className="modal-search-area">
|
||||
<TextControl
|
||||
label={__('Search for a collection', 'tainacan')}
|
||||
placeholder={ __('Search by collection\'s name', 'tainacan') }
|
||||
value={ this.state.searchCollectionName }
|
||||
onChange={(value) => {
|
||||
this.setState({
|
||||
searchCollectionName: value
|
||||
});
|
||||
_.debounce(this.fetchCollections(value), 300);
|
||||
}}/>
|
||||
<SelectControl
|
||||
label={__('Order by', 'tainacan')}
|
||||
value={ this.state.collectionOrderBy }
|
||||
options={ [
|
||||
{ label: __('Latest', 'tainacan'), value: 'date-desc' },
|
||||
{ label: __('Oldest', 'tainacan'), value: 'date' },
|
||||
{ label: __('Name (A-Z)', 'tainacan'), value: 'title' },
|
||||
{ label: __('Name (Z-A)', 'tainacan'), value: 'title-desc' }
|
||||
] }
|
||||
onChange={ ( aCollectionOrderBy ) => {
|
||||
this.state.collectionOrderBy = aCollectionOrderBy;
|
||||
this.state.collectionPage = 1;
|
||||
this.setState({
|
||||
collectionOrderBy: this.state.collectionOrderBy,
|
||||
collectionPage: this.state.collectionPage
|
||||
});
|
||||
if (this.state.searchCollectionName && this.state.searchCollectionName != '') {
|
||||
this.fetchCollections(this.state.searchCollectionName);
|
||||
} else {
|
||||
this.fetchModalCollections();
|
||||
}
|
||||
}}/>
|
||||
</div>
|
||||
{(
|
||||
this.state.searchCollectionName != '' ? (
|
||||
this.state.collections.length > 0 ?
|
||||
(
|
||||
<div>
|
||||
<div className="modal-radio-list">
|
||||
{
|
||||
<RadioControl
|
||||
selected={ this.state.temporaryCollectionId }
|
||||
options={
|
||||
this.state.collections.map((collection) => {
|
||||
return { label: collection.name, value: '' + collection.id }
|
||||
})
|
||||
}
|
||||
onChange={ ( aCollectionId ) => {
|
||||
this.setState({ temporaryCollectionId: aCollectionId });
|
||||
} } />
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
) :
|
||||
this.state.isLoadingCollections ? (
|
||||
<Spinner />
|
||||
) :
|
||||
<div className="modal-loadmore-section">
|
||||
<p>{ __('Sorry, no collection found.', 'tainacan') }</p>
|
||||
</div>
|
||||
):
|
||||
this.state.modalCollections.length > 0 ?
|
||||
(
|
||||
<div>
|
||||
<div className="modal-radio-list">
|
||||
{
|
||||
<RadioControl
|
||||
selected={ this.state.temporaryCollectionId }
|
||||
options={
|
||||
this.state.modalCollections.map((collection) => {
|
||||
return { label: collection.name, value: '' + collection.id }
|
||||
})
|
||||
}
|
||||
onChange={ ( aCollectionId ) => {
|
||||
this.setState({ temporaryCollectionId: aCollectionId });
|
||||
} } />
|
||||
}
|
||||
</div>
|
||||
<div className="modal-loadmore-section">
|
||||
<p>{ __('Showing', 'tainacan') + " " + this.state.modalCollections.length + " " + __('of', 'tainacan') + " " + this.state.totalModalCollections + " " + __('collections', 'tainacan') + "."}</p>
|
||||
{
|
||||
this.state.modalCollections.length < this.state.totalModalCollections ? (
|
||||
<Button
|
||||
isSecondary
|
||||
isSmall
|
||||
onClick={ () => this.fetchModalCollections() }>
|
||||
{__('Load more', 'tainacan')}
|
||||
</Button>
|
||||
) : null
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
) : this.state.isLoadingCollections ? <Spinner/> :
|
||||
<div className="modal-loadmore-section">
|
||||
<p>{ __('Sorry, no collection found.', 'tainacan') }</p>
|
||||
</div>
|
||||
)}
|
||||
<div className="modal-footer-area">
|
||||
<Button
|
||||
isSecondary
|
||||
onClick={ () => { this.cancelSelection() }}>
|
||||
{__('Cancel', 'tainacan')}
|
||||
</Button>
|
||||
<Button
|
||||
isPrimary
|
||||
disabled={ this.state.temporaryCollectionId == undefined || this.state.temporaryCollectionId == null || this.state.temporaryCollectionId == ''}
|
||||
onClick={ () => { this.selectCollection(this.state.temporaryCollectionId); } }>
|
||||
{ __('Select item', 'tainacan') }
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
</Modal>)
|
||||
);
|
||||
}
|
||||
}
|
|
@ -24,7 +24,9 @@ const addDataModuleToOldBlocks = () => {
|
|||
'carousel-terms-list',
|
||||
'related-items-list',
|
||||
'carousel-collections-list',
|
||||
'item-gallery'
|
||||
'item-gallery',
|
||||
'item-metadata',
|
||||
'item-metadatum'
|
||||
];
|
||||
|
||||
// Looks for Tainacan Blocks based on their classes.
|
||||
|
|
|
@ -22,7 +22,9 @@ module.exports = {
|
|||
block_item_submission_form: './src/views/gutenberg-blocks/blocks/item-submission-form/index.js',
|
||||
block_faceted_search: './src/views/gutenberg-blocks/blocks/faceted-search/index.js',
|
||||
block_carousel_terms_list: './src/views/gutenberg-blocks/blocks/carousel-terms-list/index.js',
|
||||
block_item_gallery: './src/views/gutenberg-blocks/blocks/item-gallery/index.js'
|
||||
block_item_gallery: './src/views/gutenberg-blocks/blocks/item-gallery/index.js',
|
||||
block_item_metadata: './src/views/gutenberg-blocks/blocks/item-metadata/index.js',
|
||||
block_item_metadatum: './src/views/gutenberg-blocks/blocks/item-metadatum/index.js'
|
||||
},
|
||||
output: {
|
||||
path: path.resolve(__dirname, './src/assets/js/'),
|
||||
|
|
Loading…
Reference in New Issue