Skip to content

Commit

Permalink
[Enhancement #553] Show term occurrence with label in language of the…
Browse files Browse the repository at this point in the history
… text analysis record (or file language).
  • Loading branch information
ledsoft committed Nov 20, 2024
1 parent 5a58758 commit 2f593d1
Show file tree
Hide file tree
Showing 11 changed files with 60 additions and 3 deletions.
2 changes: 2 additions & 0 deletions src/component/annotator/Annotation.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ interface AnnotationProps extends AnnotationSpanProps {
accessLevel: AccessLevel;
highlight?: boolean;
filter: AnnotatorLegendFilter;
language?: string;
}

interface AnnotationState {
Expand Down Expand Up @@ -316,6 +317,7 @@ export class Annotation extends React.Component<
onToggleDetailOpen={this.toggleOpenDetail}
onClose={this.onCloseDetail}
accessLevel={this.props.accessLevel}
language={this.props.language}
/>
);
}
Expand Down
6 changes: 5 additions & 1 deletion src/component/annotator/Annotator.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@ interface AnnotatorProps extends HasI18n {
user: User;
file: File;
vocabulary: Vocabulary;
annotationLanguage?: string;

onUpdate: (newHtml: string) => void;
setAnnotatorLegendFilter: (
Expand Down Expand Up @@ -625,7 +626,7 @@ export class Annotator extends React.Component<AnnotatorProps, AnnotatorState> {
<HeaderWithActions
title={this.renderTitle()}
className={classNames("annotator-header", {
"annotator-header-scrolled": window.pageYOffset > 0,
"annotator-header-scrolled": window.scrollY > 0,
})}
actions={[
<HighlightTermOccurrencesButton
Expand Down Expand Up @@ -708,6 +709,9 @@ export class Annotator extends React.Component<AnnotatorProps, AnnotatorState> {
onRemove={this.onRemove}
onResetSticky={this.resetStickyAnnotationId}
highlightedTerm={this.state.highlightedTerm}
annotationLanguage={
this.props.annotationLanguage || this.props.file.language
}
/>
</div>
</CardBody>
Expand Down
4 changes: 4 additions & 0 deletions src/component/annotator/AnnotatorContent.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ interface AnnotatorContentProps {
content: DomHandlerNode[];
accessLevel: AccessLevel; // The level of access rights the current user has
highlightedTerm: TermData | null;
annotationLanguage?: string;

onRemove: (annotationId: string | string[]) => void;
onUpdate: (annotationSpan: AnnotationSpanProps, term: Term | null) => void;
Expand Down Expand Up @@ -64,6 +65,7 @@ const AnnotatorContent: React.FC<AnnotatorContentProps> = (props) => {
onCreateTerm,
accessLevel,
highlightedTerm,
annotationLanguage,
} = props;

// Using memoization to skip processing and re-rendering of the content DOM in case it hasn't changed
Expand Down Expand Up @@ -112,6 +114,7 @@ const AnnotatorContent: React.FC<AnnotatorContentProps> = (props) => {
highlightedTerm !== null &&
elem.attribs.resource === highlightedTerm.iri
}
language={annotationLanguage}
{...attribs}
>
{children}
Expand Down Expand Up @@ -142,6 +145,7 @@ const AnnotatorContent: React.FC<AnnotatorContentProps> = (props) => {
onCreateTerm,
accessLevel,
highlightedTerm,
annotationLanguage,
]);

return (
Expand Down
2 changes: 2 additions & 0 deletions src/component/annotator/TermDefinitionAnnotation.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ interface TermDefinitionAnnotationProps {
text: string;
isOpen: boolean;
accessLevel: AccessLevel;
language?: string;

onRemove: () => void;
onSelectTerm: (term: Term | null) => void;
Expand Down Expand Up @@ -118,6 +119,7 @@ export const TermDefinitionAnnotation: React.FC<
term={term}
resource={props.resource}
textContent={props.text}
language={props.language}
/>
);

Expand Down
3 changes: 2 additions & 1 deletion src/component/annotator/TermDefinitionAnnotationView.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ interface TermDefinitionAnnotationViewProps {
term?: Term | null;
resource?: string;
textContent: string;
language?: string;
}

const TermDefinitionAnnotationView: React.FC<
Expand All @@ -20,7 +21,7 @@ const TermDefinitionAnnotationView: React.FC<
<tr>
<td className="label">{i18n("annotation.definition.term")}</td>
<td>
<TermLink term={props.term} />
<TermLink term={props.term} language={props.language} />
</td>
</tr>
</tbody>
Expand Down
2 changes: 2 additions & 0 deletions src/component/annotator/TermOccurrenceAnnotation.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ interface TermOccurrenceAnnotationProps {
annotationOrigin: string;
isOpen: boolean;
accessLevel: AccessLevel;
language?: string;

onRemove: () => void;
onSelectTerm: (term: Term | null) => void;
Expand Down Expand Up @@ -129,6 +130,7 @@ export const TermOccurrenceAnnotation: React.FC<
score={props.score}
resource={props.resource}
annotationClass={props.annotationClass}
language={props.language}
/>
);

Expand Down
3 changes: 2 additions & 1 deletion src/component/annotator/TermOccurrenceAnnotationView.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ interface TermOccurrenceAnnotationViewProps {
score?: string;
resource?: string;
annotationClass: string;
language?: string;
}

const TermOccurrenceAnnotationView: React.FC<
Expand All @@ -25,7 +26,7 @@ const TermOccurrenceAnnotationView: React.FC<
{i18n("annotation.term.assigned-occurrence.termLabel")}
</td>
<td>
<TermLink term={props.term!} />
<TermLink term={props.term!} language={props.language} />
</td>
</tr>
</tbody>
Expand Down
33 changes: 33 additions & 0 deletions src/component/annotator/__tests__/Annotator.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -190,6 +190,39 @@ describe("Annotator", () => {
);
});

it("passes file language to content rendering", () => {
file.language = "en";
const wrapper = shallow<Annotator>(
<Annotator
fileIri={fileIri}
vocabularyIri={vocabularyIri}
{...stateProps}
{...mockedCallbackProps}
initialHtml={generalHtmlContent}
{...intlFunctions()}
/>
);
const contentRenderer = wrapper.find(AnnotatorContent);
expect(contentRenderer.props().annotationLanguage).toEqual(file.language);
});

it("passes provided annotation language to content rendering", () => {
file.language = "en";
const wrapper = shallow<Annotator>(
<Annotator
fileIri={fileIri}
vocabularyIri={vocabularyIri}
{...stateProps}
{...mockedCallbackProps}
initialHtml={generalHtmlContent}
annotationLanguage={"cs"}
{...intlFunctions()}
/>
);
const contentRenderer = wrapper.find(AnnotatorContent);
expect(contentRenderer.props().annotationLanguage).toEqual("cs");
});

describe("on mount", () => {
const selector: TextQuoteSelector = {
exactMatch: "test-term",
Expand Down
2 changes: 2 additions & 0 deletions src/component/file/FileContentDetail.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ interface FileDetailProvidedProps {
iri: IRI;
vocabularyIri: IRI;
scrollTo?: TextQuoteSelector; // Selector of an annotation to scroll to (and highlight) after rendering
annotationLanguage?: string;
}

interface FileDetailOwnProps extends HasI18n {
Expand Down Expand Up @@ -129,6 +130,7 @@ export class FileContentDetail extends React.Component<
initialHtml={this.props.fileContent}
scrollTo={this.props.scrollTo}
onUpdate={this.onUpdate}
annotationLanguage={this.props.annotationLanguage}
/>
</>
);
Expand Down
2 changes: 2 additions & 0 deletions src/component/resource/ResourceFileDetail.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ type ResourceFileDetailProps = StoreStateProps &
interface ResourceFileDetailState {
vocabularyIri?: IRI | null;
scrollToSelector?: TextQuoteSelector;
annotationLanguage?: string;
}

export class ResourceFileDetail extends React.Component<
Expand Down Expand Up @@ -139,6 +140,7 @@ export class ResourceFileDetail extends React.Component<
if (res) {
this.setState({
vocabularyIri: VocabularyUtils.create(res.vocabularies[0].iri!),
annotationLanguage: res.language,
});
} else {
this.setState({ vocabularyIri: null });
Expand Down
4 changes: 4 additions & 0 deletions src/model/TextAnalysisRecord.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import VocabularyUtils from "../util/VocabularyUtils";
const ctx = {
vocabularies: `${VocabularyUtils.NS_TERMIT}m\u00e1-slovn\u00edk-pro-anal\u00fdzu`,
analyzedResource: `${VocabularyUtils.NS_TERMIT}m\u00e1-analyzovan\u00fd-zdroj`,
language: VocabularyUtils.DC_LANGUAGE,
};

export const CONTEXT = Object.assign({}, ctx, RESOURCE_CONTEXT);
Expand All @@ -15,18 +16,21 @@ export interface TextAnalysisRecordData {
analyzedResource: ResourceData;
vocabularies: AssetData[];
created: string;
language?: string;
}

export class TextAnalysisRecord implements TextAnalysisRecordData {
public readonly iri: string;
public readonly analyzedResource: ResourceData;
public readonly vocabularies: AssetData[];
public readonly created: string;
public readonly language?: string;

constructor(data: TextAnalysisRecordData) {
this.iri = data.iri;
this.analyzedResource = data.analyzedResource;
this.created = data.created;
this.language = data.language;
this.vocabularies = Utils.sanitizeArray(data.vocabularies);
}
}

0 comments on commit 2f593d1

Please sign in to comment.