diff --git a/common/templates/base.html b/common/templates/base.html index b61041b389bacdefb681013e12e988bf5a6fa902..216fea5020993f34c2b10fd05bf015b44ad4a2ef 100644 --- a/common/templates/base.html +++ b/common/templates/base.html @@ -104,11 +104,14 @@ </a> </nav> - <main class="container-fluid flex-grow-1 overflow-auto m-0 p-0 bg-dark" role="main"> - <div id="vue-app"></div> - {% block content %}{% endblock %} - </main> - + {% if is_vue_app %} + <main id="vue-app"></main> + {% else %} + <main class="container-fluid flex-grow-1 overflow-auto m-0 p-0 bg-dark" role="main"> + {% block content %}{% endblock %} + </main> + {% endif %} + <footer class="footer bg-dark text-muted"> <div class='px-1'> Copyright © {% trans "Instytut Podstaw Informatyki PAN" %}, 2021. diff --git a/entries/static/entries/js/components/Entries.js b/entries/static/entries/js/components/Entries.js deleted file mode 100644 index 64211efa73ac8f710e7f937a2bfface8f17b8d91..0000000000000000000000000000000000000000 --- a/entries/static/entries/js/components/Entries.js +++ /dev/null @@ -1,86 +0,0 @@ -import UnificationEntriesList from "./UnificationEntriesList.js"; -import UnificationRightPane from "./UnificationRightPane.js"; - -export default { - data () { - return { - entryId: null, - lexicalUnitId: null, - unifiedFrameId: null, - isEdit: false, - gettext: window.gettext, - unificationEntriesListRefreshKey: 1 - }; - }, - components: {UnificationEntriesList, UnificationRightPane}, - methods: { - lexicalUnitSelected (entryId, lexicalUnitId) { - this.entryId = entryId; - this.lexicalUnitId = lexicalUnitId; - this.isEdit = false; - }, - unifiedFrameSelected (unifiedFrameId) { - this.unifiedFrameId = unifiedFrameId; - this.isEdit = true; - }, - refreshEntriesList() { - this.unificationEntriesListRefreshKey++; - } - }, - mounted () { - $('#entries-list').length && Split(['#entries-list', '#entry-display'], { - sizes: [20, 80], - gutterSize: 4, - minSize: 10, - elementStyle: (dimension, size, gutterSize) => { - return { - 'flex-basis': 'calc(' + size + '% - ' + gutterSize + 'px)' - } - }, - }); - // Split(['#right-pane', '#examples'], { - // direction: 'vertical', - // sizes: [75, 25], - // gutterSize: 4, - // minSize: 10, - // }); - }, - template: ` - <div id="entries-list" class="col h-100 w-100 px-0 overflow-hidden"> - <div id="entries-list-div" class="col p-0 h-100 w-100 overflow-hidden"> - <unification-entries-list - :unificationEntriesListRefreshKey="unificationEntriesListRefreshKey" - :initialLexicalUnitId="lexicalUnitId" - :initialEntryId="entryId" - @lexical-unit-selected="lexicalUnitSelected" /> - </div> - </div> - <div id="entry-display" class="col h-100 p-0 overflow-hidden"> - <div class="w-100 h-100"> - <div id="right-pane" class="col w-100 h-100 p-0"> - <unification-right-pane - :key="lexicalUnitId" - :entryId="entryId" - :lexicalUnitId="lexicalUnitId" - :initialUnifiedFrameId="unifiedFrameId" - :initialIsEdit="isEdit" - @refresh-entries-list="refreshEntriesList" /> - </div> -<!-- <div class="col w-100 p-0 tab-pane overflow-auto" id="examples">--> -<!-- <table id="semantics-examples" class="table table-sm table-hover">--> -<!-- <thead>--> -<!-- <tr>--> -<!-- <th scope="col">{{ gettext("Przykład") }}<i id="examples-argument"></i><i id="examples-lu"></i><i id="examples-schema"></i></th>--> -<!-- <th scope="col">{{ gettext("Źródło") }}</th>--> -<!-- <th scope="col">{{ gettext("Opinia") }}</th>--> -<!-- </tr>--> -<!-- </thead>--> -<!-- <tbody id="semantics-examples-list">--> -<!-- </tbody>--> -<!-- </table>--> -<!-- <p class="mx-1 my-1" id="semantics-no-examples">{{ gettext("Brak przykładów") }}</p>--> -<!-- </div>--> - </div> - </div> - ` -}; diff --git a/entries/static/entries/js/components/InfoTooltip.js b/entries/static/entries/js/components/InfoTooltip.js deleted file mode 100644 index 3fa1e9a415277b2cf2b13cfdb7d2f7f27360e25e..0000000000000000000000000000000000000000 --- a/entries/static/entries/js/components/InfoTooltip.js +++ /dev/null @@ -1,31 +0,0 @@ -export default { - props: { - text: String, - visibleText: String - }, - data () { - return { - iconUrl: window.STATIC_URL + 'common/img/info.svg' - } - }, - computed: { - quotedText () { - return this.text.replace(/"/g, '"'); - } - }, - mounted () { - $(this.$refs.tooltip).tooltip(); - }, - template: ` - <span - data-toggle="tooltip" - data-placement="bottom" - data-html="true" - :title="quotedText" - ref="tooltip" - > - <img v-if="!visibleText" :src="iconUrl" alt="info" width="14" height="14" /> - <span v-else>{{visibleText}}</span> - </span> - ` -} diff --git a/entries/static/entries/js/components/Spinner.js b/entries/static/entries/js/components/Spinner.js deleted file mode 100644 index a4ac913a5ac7bf63b5db38266f9846e9839850cf..0000000000000000000000000000000000000000 --- a/entries/static/entries/js/components/Spinner.js +++ /dev/null @@ -1,12 +0,0 @@ -export default { - data() { - return { gettext: window.gettext } - }, - template: ` - <div class="d-flex justify-content-center wait-spinner"> - <div class="spinner-border text-primary m-5" style="width: 3rem; height: 3rem;" role="status"> - <span class="sr-only">{{ gettext('Proszę czekać...') }}</span> - </div> - </div> - ` -} diff --git a/entries/static/entries/js/components/UnificationEntriesList.js b/entries/static/entries/js/components/UnificationEntriesList.js deleted file mode 100644 index 5bec7892450fd2a2ddb67da7a9a1bb5e292c4dc3..0000000000000000000000000000000000000000 --- a/entries/static/entries/js/components/UnificationEntriesList.js +++ /dev/null @@ -1,48 +0,0 @@ -export default { - props: { - initialLexicalUnitId: Number, - initialEntryId: Number, - unificationEntriesListRefreshKey: Number, - }, - watch: { - unificationEntriesListRefreshKey() { - // TODO: reload data and click in selected row - // this.datatableObject.ajax.reload(); - setup_entries_list({ - table: this.$refs.table, - lexicalUnitSelected: (entryId, lexicalUnitId) => { this.$emit('lexicalUnitSelected', entryId, lexicalUnitId); }, - selectEntryId: this.initialEntryId, - secondarySelectEntryId: this.initialLexicalUnitId, - }); - } - }, - data () { - return { - gettext: window.gettext, - canViewAssignment: has_permission("users.view_assignment"), - } - }, - emits: ['lexicalUnitSelected'], - mounted () { - setup_entries_list({ - table: this.$refs.table, - lexicalUnitSelected: (entryId, lexicalUnitId) => { this.$emit('lexicalUnitSelected', entryId, lexicalUnitId); }, - selectEntryId: this.initialEntryId - }); - }, - template: ` - <table ref="table" class="table table-sm text-dark"> - <thead> - <tr> - <th class="p-1">{{ gettext('Lemat') }}</th> - <th class="p-1">{{ gettext('Część mowy') }}</th> - <th class="p-1">{{ gettext('Do pobrania') }}</th> - <th v-if="canViewAssignment" class="p-1">{{ gettext('Semantyk') }}</th> - <th v-else class="p-1">{{ gettext('Moje (w opracowaniu)') }}</th> - </tr> - </thead> - <tbody id="entries"> - </tbody> - </table> - ` -}; diff --git a/entries/static/entries/js/components/UnificationFramesList.js b/entries/static/entries/js/components/UnificationFramesList.js deleted file mode 100644 index e0059fd381a251b66a670e0b1a3066ddddf2a775..0000000000000000000000000000000000000000 --- a/entries/static/entries/js/components/UnificationFramesList.js +++ /dev/null @@ -1,45 +0,0 @@ -export default { - props: { - initialUnifiedFrameId: Number, - unificationEntriesListRefreshKey: Number, - }, - data () { - return { - gettext: window.gettext, - canViewAssignment: has_permission("users.view_assignment") - } - }, - watch: { - unificationEntriesListRefreshKey() { - // TODO: reload data and click in selected row - // this.datatableObject.ajax.reload(); - setup_frames_list({ - table: this.$refs.table, - unifiedFrameSelected: (unifiedFrameId) => { this.$emit('unifiedFrameSelected', unifiedFrameId); }, - selectEntryId: this.initialEntryId, - }); - } - }, - emits: ['unifiedFrameSelected'], - mounted () { - setup_frames_list({ - table: this.$refs.table, - unifiedFrameSelected: (unifiedFrameId) => { this.$emit('unifiedFrameSelected', unifiedFrameId); }, - selectEntryId: this.initialUnifiedFrameId, - }); - }, - template: ` - <table ref="table" class="table table-sm table-hover text-dark"> - <thead> - <tr> - <th class="p-1">{{ gettext('Rama') }}</th> - <th class="p-1">{{ gettext('Status') }}</th> - <th v-if="canViewAssignment" class="p-1">{{ gettext('Leksykograf') }}</th> - <th class="p-1" hidden="true">{{ gettext('Id') }}</th> - </tr> - </thead> - <tbody id="entries"> - </tbody> - </table> - ` -}; diff --git a/entries/static/entries/js/components/UnificationRightPane.js b/entries/static/entries/js/components/UnificationRightPane.js deleted file mode 100644 index 9f99ede3508ff8323a9239c4948ff3388e1306a3..0000000000000000000000000000000000000000 --- a/entries/static/entries/js/components/UnificationRightPane.js +++ /dev/null @@ -1,78 +0,0 @@ -import LexicalUnitDisplay from './LexicalUnitDisplay.js'; -import LexicalUnitEdit from './LexicalUnitEdit.js'; - -export default { - components: {LexicalUnitDisplay, LexicalUnitEdit}, - props: { - entryId: Number, - lexicalUnitId: Number, - initialUnifiedFrameId: Number, - initialIsEdit: false, - }, - emits: ['refreshEntriesList'], - data () { - return this.getInitialData(); - }, - methods: { - getInitialData () { - return { - isEdit: this.initialIsEdit, - key: this.lexicalUnitId, - entryIdLocal: this.entryId, - unifiedFrameId: this.initialUnifiedFrameId, - previewedUnifiedFrameId: null - }; - }, - goToDisplay () { - this.isEdit = false; - this.unifiedFrameId = null; - }, - refresh () { - this.key = null; - setTimeout(() => { this.key = this.lexicalUnitId; }, 0); - }, - swapFrames (previewedUnifiedFrameId) { - this.previewedUnifiedFrameId = this.unifiedFrameId; - this.unifiedFrameId = previewedUnifiedFrameId; - this.refresh(); - }, - refreshEntriesList() { - this.$emit('refreshEntriesList'); - } - }, - watch: { - initialIsEdit () { - Object.assign(this, this.getInitialData()); - }, - lexicalUnitId () { - Object.assign(this, this.getInitialData()); - }, - initialUnifiedFrameId () { - Object.assign(this, this.getInitialData()); - } - }, - template: ` - <div v-if="key || unifiedFrameId" :key="(key, entryIdLocal, unifiedFrameId, isEdit)" class="row h-100 m-0 p-0 overflow-auto" id="semantics-top-pane"> - <lexical-unit-display - v-if="key && !isEdit" - :key="key" - :entryId="entryIdLocal" - :lexicalUnitId="key" - @refresh="refresh" - @refresh-entries-list="refreshEntriesList" - /> - <lexical-unit-edit - ref="lexicalUnitEdit" - v-if="unifiedFrameId && isEdit" - :key="unifiedFrameId" - :readOnly="false" - :unifiedFrameId="unifiedFrameId" - :previewedUnifiedFrameId="previewedUnifiedFrameId" - :initialRightPaneTab="previewedUnifiedFrameId && unifiedFrameId !== previewedUnifiedFrameId ? 'frame_preview' : 'schemata'" - @go-to-display="goToDisplay" - @swap-frames="swapFrames" - @refresh-entries-list="refreshEntriesList" - /> - </div> - ` -} diff --git a/entries/static/entries/js/components/UnificationSwitchableList.js b/entries/static/entries/js/components/UnificationSwitchableList.js deleted file mode 100644 index e044e9e700775f9770b2a3c1410750cbb71dc666..0000000000000000000000000000000000000000 --- a/entries/static/entries/js/components/UnificationSwitchableList.js +++ /dev/null @@ -1,40 +0,0 @@ -import UnificationEntriesForFramesList from "./UnificationEntriesForFramesList.js"; -import UnificationEntriesList from "./UnificationEntriesList.js"; -import UnificationFramesList from "./UnificationFramesList.js"; - -export default { - props: { - initialLexicalUnitId: Number, - initialEntryId: Number, - unificationEntriesListRefreshKey: Number, - }, - data () { - return { - gettext: window.gettext, - isFrameView: false - } - }, - emits: ['lexicalUnitSelected', 'unifiedFrameSelected', 'refreshEntriesList'], - methods: { - lexicalUnitSelected (entryId, lexicalUnitId) { - this.$emit('lexicalUnitSelected', entryId, lexicalUnitId); - }, - unifiedFrameSelected (unifiedFrameId, entryId, lexicalUnitId) { - this.$emit('unifiedFrameSelected', unifiedFrameId, entryId, lexicalUnitId); - }, - }, - components: {UnificationEntriesList, UnificationEntriesForFramesList, UnificationFramesList}, - template: ` - <label class="mt-2 position-absolute" style="z-index: 2"><input type="checkbox" v-model="isFrameView" /> {{ gettext('RAMY') }}</label> - <div v-if="!isFrameView" class="h-100"><unification-entries-for-frames-list - :unificationEntriesListRefreshKey="unificationEntriesListRefreshKey" - :initialLexicalUnitId="initialLexicalUnitId" - :initialEntryId="initialEntryId" - @unified-frame-selected="unifiedFrameSelected" - /></div> - <div v-else class="h-100"><unification-frames-list - :unificationEntriesListRefreshKey="unificationEntriesListRefreshKey" - @unified-frame-selected="unifiedFrameSelected" - /></div> - ` -}; diff --git a/entries/static/entries/js/components/frame-components/ExamplesComponent.js b/entries/static/entries/js/components/frame-components/ExamplesComponent.js deleted file mode 100644 index 81ff812bcc524d306a81605638949cd65e3c3c02..0000000000000000000000000000000000000000 --- a/entries/static/entries/js/components/frame-components/ExamplesComponent.js +++ /dev/null @@ -1,92 +0,0 @@ -import InfoTooltip from "../InfoTooltip.js"; - -export default { - props: { - examples: Object, - frame: Object, - frame_arguments: Object, - frame_arguments_or_type: null, - schemas: Object, - lus: Object, - }, - components: {InfoTooltip}, - data() { - return { - img_prefix: String - } - }, - emits: ['exampleSelected'], - methods: { - getExamples () { - let ret = this.examples; - if(this.schemas && this.schemas.length > 0) { - // ograniczone do schematu - ret = ret.filter(e => this.schemas.every(a => e.schema_ids.includes(parseInt(a.id)))); - } - if(this.frame_arguments && this.frame_arguments.length > 0) { - // ograniczone do argumentu ramy - if(this.frame_arguments_or_type) { - ret = ret.filter(e => this.frame_arguments.some(a => e.argument_ids.includes(a.id))); - } else { - ret = ret.filter(e => this.frame_arguments.every(a => e.argument_ids.includes(a.id))); - } - } - if(this.frame) { - ret = ret.filter(e => e.frame_ids.includes(this.frame.id)); - } - if(this.lus && this.lus.length > 0) { - ret = ret.filter(e => this.lus.every(lu => e.lu_ids.includes(lu.id))); - } - return ret; - }, - getSchemaStr(schema) { - return schema.positions.map(e => e.phrases.map(p => p.str).join(",")).join('|'); - }, - selectExample(example) { - example.selected = !example.selected; - this.$emit('exampleSelected', this.examples.filter(example => example.selected)); - } - }, - mounted () { - this.img_prefix = window.STATIC_URL; - }, - template: ` - <table id="semantics-examples" v-if="getExamples().length > 0" class="table table-sm table-hover" style=""> - <thead> - <tr> - <th scope="col">Przykład - <i v-if="frame_arguments" v-for="frame_argument in frame_arguments"> - <span class="example-role"> {{' '}} - <span :class="frame_argument.role">{{frame_argument.role}}</span> - </span> - </i> - <i v-if="lus" v-for="lu in lus">{{' ' + lu.str}}</i> - <i v-if="schemas" v-for="schema in schemas">{{' '+getSchemaStr(schema)}}</i> - </th> - <th scope="col">Źródło</th> - <th scope="col">Opinia</th> - </tr> - </thead> - <tbody id="semantics-examples-list"> - <template v-for="example in getExamples()"> - <tr class="example" - @mouseenter="example.hover=true" - @mouseleave="example.hover=false" - @click.stop="selectExample(example)" - :class="example.selected ? 'active table-primary' : example.hover ? 'bg-highlight' : ''" - > - <td class="py-1"> - {{example.sentence}} - <info-tooltip v-if="example.note" :text="example.note" /> - </td> - <td class="py-1">{{example.source}}</td> - <td class="py-1">{{example.opinion}}</td> - </tr> - </template> - </tbody> - </table> - <p v-else class="mx-1 my-1" id="semantics-no-examples" style="display: none;">Brak przykładów</p> - ` -} - - diff --git a/entries/static/entries/js/components/frame-components/SemanticsSchemataComponent.js b/entries/static/entries/js/components/frame-components/SemanticsSchemataComponent.js deleted file mode 100644 index 9f1d160d3841e8c830221e0024d32c0a89bf1501..0000000000000000000000000000000000000000 --- a/entries/static/entries/js/components/frame-components/SemanticsSchemataComponent.js +++ /dev/null @@ -1,173 +0,0 @@ -import InfoTooltip from "../InfoTooltip.js"; - -export default { - props: { - subentries: Object, - frame: Object, - alternations: Object, - realisation_phrases: Object, - realisation_descriptions: Object, - selectedExamples: Object - }, - components: {InfoTooltip}, - emits: ['schemataSelected'], - data() { - return { - img_prefix: String - } - }, - methods: { - getFunctions(position) { - const props_spans = []; - if (position.func.str !== '') { - props_spans.push({str: position.func.str, tooltip: position.func.desc}); - } - if (position.control.str !== '') { - props_spans.push({str: position.control.str, tooltip: position.control.desc}); - } - if (position.p_control.str !== '') { - props_spans.push({str: position.p_control.str, tooltip: position.p_control.desc}); - } - return props_spans; - }, - getSchemataPositionCnt(schema) { - return schema.positions.length; - }, - getRealisationDescriptions(schema) { - const alternationDescList = []; - if(this.alternations) { - const curr_alternations = this.alternations[this.frame.id][schema.id]; - const curr_realisation_descriptions = this.realisation_descriptions[this.frame.id][schema.id]; - for (let i in curr_alternations) { - alternationDescList.push(curr_realisation_descriptions[i]); - } - } - return '<i>' + alternationDescList + '</i>'; - }, - getPhraseCss(schema, position) { - const styles = []; - if(this.alternations) { - const argumentIdSet = new Set(); - - const curr_alternations = this.alternations[this.frame.id][schema.id]; - for (let i in curr_alternations) { - const alternation = curr_alternations[i] - - for (let arg_id in alternation){ - const phrase_ids = alternation[arg_id]; - phrase_ids.forEach(phrase_id => { - if (phrase_id.startsWith(position.id)) { - argumentIdSet.add(arg_id); - } - }); - } - } - - argumentIdSet.forEach(argumentId => { - const argument = this.frame.arguments.find(arg => argumentId.endsWith(arg.argument_id)); - const role = argument.role; - styles.push(role); - }); - - } - const selectedExampleFrameArguments = this.selectedExamples && this.selectedExamples.length > 0 ? new Set(this.selectedExamples.map(e => e.positions).flat()) : null; - - if(selectedExampleFrameArguments != null) { - styles.push(selectedExampleFrameArguments.has(position.id) ? 'example-yes' : 'example-no'); - } - return styles; - }, - getPositionPhrases(schema, position) { - const phrases = []; - if(this.alternations) { - const curr_alternations = this.alternations[this.frame.id][schema.id]; - for (let i in curr_alternations) { - const alternation = curr_alternations[i] - - for (let arg_id in alternation){ - const phrase_ids = alternation[arg_id]; - phrase_ids.forEach(phrase_id => { - if (phrase_id.startsWith(position.id)) { - phrases.push(this.realisation_phrases[arg_id][i][phrase_id]); - } - }); - } - } - } - return phrases; - }, - selectSchema(schema) { - schema.selected = !schema.selected; - const selected = []; - this.subentries.forEach(subentry => { - subentry.schemata.forEach(s => { - if(s.selected) { - selected.push(s); - } - }); - }); - this.$emit('schemataSelected', selected); - } - }, - mounted () { - this.img_prefix = window.STATIC_URL; - }, - template: ` - <div> - <template v-for="subentry in subentries"> - <div class="subentry"> - <div class="mb-1 sticky-top"><h5 class="bg-dark text-light p-1">{{subentry.str}}</h5></div> - <template v-for="schema in subentry.schemata"> - <div class="schema mb-3" - v-if="alternations[this.frame.id][schema.id]" - @mouseenter="schema.hover=true" - @mouseleave="schema.hover=false" - @click="selectSchema(schema)" - :class="(schema.selected ? 'active' : schema.hover ? 'bg-highlight' : '')" - > - <table class="table m-0 table-borderless border border-secondary text-dark"> - <tbody> - <tr class="opinion-row"> - <th scope="row" class="py-2 px-1 text-secondary" style="width: 3em;">Opinia</th> - <td class="opinion-cell py-2 px-1" :colspan="getSchemataPositionCnt(schema)"><img - :src="img_prefix + 'entries/img/' + schema.opinion_key + '.svg'" width="12" - height="12" :alt="schema.opinion"> {{schema.opinion}} - </td> - </tr> - - <tr> - <th scope="row" class="py-2 px-1 text-secondary">Funkcja</th> - - <td class="position py-2 px-1 border-top border-left border-secondary" - v-for="position in schema.positions"> - <div v-for="f in getFunctions(position)" class="phrase px-1 py-2"> - <info-tooltip :text="f.tooltip" :visibleText="f.str"/> - </div> - </td> - - </tr> - - <tr class="realisation-description"> - <td class="px-1 py-2" :colspan="getSchemataPositionCnt(schema)" v-html="getRealisationDescriptions(schema)"></td> - </tr> - <tr class="phrase-types alt-0"> - <th scope="row" class="py-0 px-1 text-secondary">Typy fraz</th> - <td v-for="position in schema.positions" class="px-0 py-0 border-top border-left border-secondary"> - <div v-for="phrase in position.phrases" class="phrase px-1 py-2" - :class="getPhraseCss(schema, position)"> - <info-tooltip :text="phrase.desc" :visibleText="phrase.str"/> - </div> - <div v-for="phrase in getPositionPhrases(schema, position)" class="realisation-phrase px-1 py-2"><i>{{phrase}}</i></div> - </td> - </tr> - </tbody> - </table> - </div> - </template> - </div> - </template> - </div> - ` -} - - diff --git a/entries/static/entries/js/unification.js b/entries/static/entries/js/unification.js index 512cd6292d42ced11533aa0ddcbee837a23d3a75..9dd53ad6cff611cdac66f4a4db47609d163dc3e7 100644 --- a/entries/static/entries/js/unification.js +++ b/entries/static/entries/js/unification.js @@ -1,46 +1,5 @@ "use strict"; -function get_unified_frame(unified_frame_id, related) { - check_import_status(); - clear_entry(); - show_entry_spinners(); - //const data = { 'forms' : serialize_forms($('#main-form')), 'entry' : entry_id }; - const data = { 'unified_frame_id' : unified_frame_id, 'no_filters' : related }; - $.ajax({ - type : 'post', - url : '/' + lang + '/unifier/get_unified_frame/', - dataType : 'json', - data : data, - timeout : 60000, - success : function(response) { - curr_entry = unified_frame_id; - curr_no_filters = related; - clear_info(); - curr_alternations = response.alternations; - curr_realisation_phrases = response.realisation_phrases; - curr_realisation_descriptions = response.realisation_descriptions; - curr_examples = response.examples; - curr_examples_by_id = Object(); - for (let i in curr_examples) { - curr_examples_by_id[curr_examples[i].id] = curr_examples[i]; - } - // show_syntax(response.subentries); - show_unified_frame(response.unified_frame, response.frames) - show_unified_frame_lexical_units(response.frames) - fulfill_slowal_frames_arguments_with_empty_elems(response.unified_frame, response.frames) - show_semantics_unified_view(response.frames, response.subentries); - // show_unmatched_examples(); - - // tooltips with meaning gloss - activate_tooltips($('#semantics-frames-pane')); - update_last_visited(response.last_visited); - }, - error: function(request, errorType, errorMessage) { - show_error(errorType + ' (' + errorMessage + ')'); - } - }); -} - function slowal_frames2selecional_preferencies(unified_frame, slowal_frames) { const unified_argument_2_selecional_preferencies = {} diff --git a/entries/static/entries/js/utils.js b/entries/static/entries/js/utils.js index 694904e3a929fa26be0780e87fb24e0f8dd2a6b7..18faac7196d0a272d84bdb8e8c1f34d0ebbf219a 100644 --- a/entries/static/entries/js/utils.js +++ b/entries/static/entries/js/utils.js @@ -30,13 +30,3 @@ function normalizeFormData(data) { } } } - -function indexOfId(array, id) { - var i; - for (i = 0; i < array.length; i++) { - if (array[i].id == id) { - return i; - } - } - return -1; -} diff --git a/entries/templates/entries.html b/entries/templates/entries.html index 8c164780711889ef776566e510df5131af86c683..b7ecd7826c414921a2c3a228477a19ecae2d09fe 100644 --- a/entries/templates/entries.html +++ b/entries/templates/entries.html @@ -16,6 +16,7 @@ <script type="module" src="{% static 'entries/js/entries_index.js' %}"></script> {% endblock %} -{% block content %} +{% block modals %} + {{ block.super }} <div id="lexical-unit-notes-template" class="d-none">{% include 'notes.html' %}</div> {% endblock %} diff --git a/entries/templates/entries_base.html b/entries/templates/entries_base.html index 2df1529b641a36758ffc1203af32ba0a50385d8d..b46559a6c66c07047c2d29e5564328bc95d7595a 100644 --- a/entries/templates/entries_base.html +++ b/entries/templates/entries_base.html @@ -22,7 +22,6 @@ <script type="text/javascript" src="https://cdn.datatables.net/v/bs4/dt-1.12.1/sc-2.0.3/datatables.min.js"></script> <script type="text/javascript" src="https://cdn.datatables.net/plug-ins/1.12.1/features/scrollResize/dataTables.scrollResize.min.js"></script> <script src="{% static 'common/js/csrf.js' %}"></script> - <!--script src="{% static 'entries/js/panels.js' %}"></script--> <script src="{% static 'entries/js/forms.js' %}"></script> <script src="{% static 'entries/js/utils.js' %}"></script> <script src="{% static 'entries/js/entries.js' %}"></script> diff --git a/entries/templates/test.html b/entries/templates/test.html deleted file mode 100644 index c3c96aaf6ff5973fc2d3e7260cd688dc917ea496..0000000000000000000000000000000000000000 --- a/entries/templates/test.html +++ /dev/null @@ -1,23 +0,0 @@ -{% load static %} - -<!doctype html> - -{% load static %} - -<html lang="pl"> -<head> - <meta charset="utf-8"> - <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no"> - <link rel="icon" href="{% static 'common/favicon.ico' %}"> - <link rel="stylesheet" href="//code.jquery.com/ui/1.12.1/themes/smoothness/jquery-ui.css"> - <link rel="stylesheet" type="text/css" href="https://bootswatch.com/4/lux/bootstrap.min.css"> - <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script> - <!--might be needed for resizeable panels, causes errors if included after Popper--> - <script src="https://ajax.googleapis.com/ajax/libs/jqueryui/1.12.1/jquery-ui.min.js"></script> - <script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js" integrity="sha384-JjSmVgyd0p3pXB1rRibZUAYoIIy6OrQ6VrjIEaFf/nJGzIxFDsf4x0xIM+B07jRM" crossorigin="anonymous"></script> - <script src="{% static 'entries/js/entries.js' %}"></script> -</head> - -<body> - <input class="regex-autocomplete" data-autocomplete="phrasetype"> -</body> diff --git a/entries/templates/unification.html b/entries/templates/unification.html index 91abfafe2745bd5bb6275d93e3dd65de76502506..1f48626e3f3c907249bd095590db6204f863300c 100644 --- a/entries/templates/unification.html +++ b/entries/templates/unification.html @@ -20,6 +20,7 @@ <script type="module" src="{% static 'entries/js/unification_index.js' %}"></script> {% endblock %} -{% block content %} +{% block modals %} + {{ block.super }} <div id="lexical-unit-notes-template" class="d-none">{% include 'notes.html' %}</div> {% endblock %} diff --git a/entries/views.py b/entries/views.py index 947632ab4f60006f32437d853d88d0a2290eead1..5430b0109f26927229d996ab1e9025de26be55b6 100644 --- a/entries/views.py +++ b/entries/views.py @@ -47,10 +47,6 @@ from .phrase_descriptions.descriptions import position_prop_description MAX_LAST_VISITED = 10 -# TODO remove!!! -#def test(request): -# return render(request, 'test.html', {}) - @login_required def entries(request): # TODO make this automatic by subclassing/configuring session object @@ -67,6 +63,7 @@ def entries(request): request, 'entries.html', { + 'is_vue_app': True, 'entries_form' : EntryForm(), 'frames_form' : FrameFormFactory.get_form(as_subform=False), 'schemata_form' : SchemaFormFactory.get_form(as_subform=False) @@ -79,6 +76,7 @@ def unification(request): request, 'unification.html', { + 'is_vue_app': True, 'unified_frame_id': request.GET.get("unified_frame_id"), 'entries_form' : EntryForm(), 'frames_form': FrameFormFactory.get_form(as_subform=False), diff --git a/frontend/src/App.vue b/frontend/src/App.vue index e5f945f81c74dd1ae38da8a05b91179cc89c4a19..4cbe12a114a7e7b03fa973823e298f9234baec9e 100644 --- a/frontend/src/App.vue +++ b/frontend/src/App.vue @@ -1,7 +1,5 @@ <template> - <div class="row m-0 p-0 h-100" v-if="this.$route.name !== '404'"> - <div class="container bg-light"> - <RouterView /> - </div> - </div> + <div class="row h-100 bg-light" v-if="this.$route.name !== '404'"> + <RouterView /> + </div> </template> diff --git a/frontend/src/components/Entries.vue b/frontend/src/components/Entries.vue deleted file mode 100644 index 3dc2db658d0f8fc56025d6710484f6cbf9e3b496..0000000000000000000000000000000000000000 --- a/frontend/src/components/Entries.vue +++ /dev/null @@ -1,3 +0,0 @@ -<template> - Entries -</template> diff --git a/frontend/src/components/Unification.vue b/frontend/src/components/Unification.vue deleted file mode 100644 index 23eff7f5e81b02175a8b44bd729a5666db18d781..0000000000000000000000000000000000000000 --- a/frontend/src/components/Unification.vue +++ /dev/null @@ -1,3 +0,0 @@ -<template> - Unification -</template> diff --git a/frontend/src/components/shared/InfoTooltip.vue b/frontend/src/components/shared/InfoTooltip.vue new file mode 100644 index 0000000000000000000000000000000000000000..f16137649d74d8ae6d909fdf7bda77f8e93af098 --- /dev/null +++ b/frontend/src/components/shared/InfoTooltip.vue @@ -0,0 +1,34 @@ +<script> + export default { + props: { + text: String, + visibleText: String + }, + data () { + return { + iconUrl: window.STATIC_URL + 'common/img/info.svg' + } + }, + computed: { + quotedText () { + return this.text.replace(/"/g, '"'); + } + }, + mounted () { + $(this.$refs.tooltip).tooltip(); + }, + } +</script> + +<template> + <span + data-toggle="tooltip" + data-placement="bottom" + data-html="true" + :title="quotedText" + ref="tooltip" + > + <img v-if="!visibleText" :src="iconUrl" alt="info" width="14" height="14" /> + <span v-else>{{visibleText}}</span> + </span> +</template> \ No newline at end of file diff --git a/frontend/src/components/unification/Entries/Entries.vue b/frontend/src/components/unification/Entries/Entries.vue new file mode 100644 index 0000000000000000000000000000000000000000..fde7135e908da3dc675a26fe10c071ad13732bfc --- /dev/null +++ b/frontend/src/components/unification/Entries/Entries.vue @@ -0,0 +1,76 @@ +<script> +import EntriesList from "./EntriesList.vue"; +import LexicalUnitDisplay from "../shared/LexicalUnitDisplay.vue"; + +export default { + data () { + return { + entryId: null, + lexicalUnitId: null, + unifiedFrameId: null, + isEdit: false, + gettext: window.gettext, + key: null, + unificationEntriesListRefreshKey: 1 + }; + }, + components: {EntriesList, LexicalUnitDisplay}, + methods: { + lexicalUnitSelected (entryId, lexicalUnitId) { + this.entryId = entryId; + this.lexicalUnitId = lexicalUnitId; + this.key = lexicalUnitId; + this.isEdit = false; + }, + unifiedFrameSelected (unifiedFrameId) { + this.unifiedFrameId = unifiedFrameId; + this.isEdit = true; + }, + refreshEntriesList() { + this.unificationEntriesListRefreshKey++; + }, + refresh () { + this.key = null; + setTimeout(() => { this.key = this.lexicalUnitId; }, 0); + }, + }, + mounted () { + $('#entries-list').length && Split(['#entries-list', '#entry-display'], { + sizes: [20, 80], + gutterSize: 4, + minSize: 10, + elementStyle: (dimension, size, gutterSize) => { + return { + 'flex-basis': 'calc(' + size + '% - ' + gutterSize + 'px)' + } + }, + }); + }, +}; +</script> + +<template> + <div id="entries-list" class="col h-100 w-100 pr-0 overflow-hidden"> + <div id="entries-list-div" class="h-100 w-100 overflow-hidden"> + <entries-list + :unificationEntriesListRefreshKey="unificationEntriesListRefreshKey" + :initialLexicalUnitId="lexicalUnitId" + :initialEntryId="entryId" + @lexical-unit-selected="lexicalUnitSelected" /> + </div> + </div> + <div id="entry-display" class="col h-100 p-0 overflow-hidden"> + <div class="w-100 h-100"> + <div id="right-pane" class="col w-100 h-100 p-0"> + <lexical-unit-display + v-if="lexicalUnitId" + :key="key" + :entryId="entryId" + :lexicalUnitId="lexicalUnitId" + @refresh="refresh" + @refresh-entries-list="refreshEntriesList" + /> + </div> + </div> + </div> +</template> diff --git a/frontend/src/components/unification/Entries/EntriesList.vue b/frontend/src/components/unification/Entries/EntriesList.vue new file mode 100644 index 0000000000000000000000000000000000000000..41d3175194ed9632185fdc9cc207e52b7fa32acb --- /dev/null +++ b/frontend/src/components/unification/Entries/EntriesList.vue @@ -0,0 +1,51 @@ +<script> + export default { + props: { + initialLexicalUnitId: Number, + initialEntryId: Number, + unificationEntriesListRefreshKey: Number, + }, + watch: { + unificationEntriesListRefreshKey() { + // TODO: reload data and click in selected row + // this.datatableObject.ajax.reload(); + setup_entries_list({ + table: this.$refs.table, + lexicalUnitSelected: (entryId, lexicalUnitId) => { this.$emit('lexicalUnitSelected', entryId, lexicalUnitId); }, + selectEntryId: this.initialEntryId, + secondarySelectEntryId: this.initialLexicalUnitId, + }); + } + }, + data () { + return { + gettext: window.gettext, + canViewAssignment: has_permission("users.view_assignment"), + } + }, + emits: ['lexicalUnitSelected'], + mounted () { + setup_entries_list({ + table: this.$refs.table, + lexicalUnitSelected: (entryId, lexicalUnitId) => { this.$emit('lexicalUnitSelected', entryId, lexicalUnitId); }, + selectEntryId: this.initialEntryId + }); + }, + }; +</script> + +<template> + <table ref="table" class="table table-sm text-dark"> + <thead> + <tr> + <th class="p-1">{{ gettext('Lemat') }}</th> + <th class="p-1">{{ gettext('Część mowy') }}</th> + <th class="p-1">{{ gettext('Do pobrania') }}</th> + <th v-if="canViewAssignment" class="p-1">{{ gettext('Semantyk') }}</th> + <th v-else class="p-1">{{ gettext('Moje (w opracowaniu)') }}</th> + </tr> + </thead> + <tbody id="entries"> + </tbody> + </table> +</template> diff --git a/entries/static/entries/js/components/LexicalUnitEdit.js b/frontend/src/components/unification/Unification/LexicalUnitEdit.vue similarity index 95% rename from entries/static/entries/js/components/LexicalUnitEdit.js rename to frontend/src/components/unification/Unification/LexicalUnitEdit.vue index 59f99fa63c38a7e61b09807ddf68ce714579b329..6db0f6bab5e21eb94f95ca6bc7c1f2bd1778eb1b 100644 --- a/entries/static/entries/js/components/LexicalUnitEdit.js +++ b/frontend/src/components/unification/Unification/LexicalUnitEdit.vue @@ -1,71 +1,15 @@ -import InfoTooltip from "./InfoTooltip.js"; -import Spinner from "./Spinner.js"; -import UnificationSwitchableList from "./UnificationSwitchableList.js"; -import ExamplesComponent from "./frame-components/ExamplesComponent.js"; -import SlowalFrameComponent from "./frame-components/SlowalFrameComponent.js"; -import SemanticsSchemataComponent from "./frame-components/SemanticsSchemataComponent.js"; -import MeaningComponent from "./frame-components/MeaningComponent.js"; -import SelectionalPreference from "../selectional_preference.js"; - +<script> +import InfoTooltip from "../../shared/InfoTooltip.vue"; +import Spinner from "../../shared/Spinner.vue"; +import ExamplesComponent from "../shared/frame-components/ExamplesComponent.vue"; +import SlowalFrameComponent from "../shared/frame-components/SlowalFrameComponent.vue"; +import SemanticsSchemataComponent from "../shared/frame-components/SemanticsSchemataComponent.vue"; +import MeaningComponent from "../shared/frame-components/MeaningComponent.vue"; +import SelectionalPreference from "./SelectionalPreference.js"; +import UnificationFramePreview from "./UnificationFramePreview.vue"; let LexicalUnitEdit = {}; -const FramePreview = { - props: { - initialUnifiedFrameId: Number, - initialLexicalUnitId: Number, - forceRefresh: Number - }, - data () { - return { - unifiedFrameId: this.initialUnifiedFrameId - }; - }, - components: {LexicalUnitEdit, UnificationSwitchableList}, - emits: ['changeFrame', 'refreshEntriesList'], - methods: { - unifiedFrameSelected (unifiedFrameId) { - this.$emit('changeFrame', unifiedFrameId); - }, - refreshEntriesList() { - this.$emit('refreshEntriesList') - }, - }, - mounted () { - Split(['#frame-preview-left-pane', '#frame-preview-right-pane'], { - sizes: [60, 40], - minSize: 20, - gutterSize: 4, - elementStyle: (dimension, size, gutterSize) => { - return { - 'flex-basis': 'calc(' + size + '% - ' + gutterSize + 'px)' - } - }, - }); - }, - template: ` - <div class="row h-100 overflow-hidden"> - <div :key="unifiedFrameId" class="col h-100 pr-0 pt-0 pb-0 overflow-auto" id="frame-preview-left-pane"> - <lexical-unit-edit - v-if="unifiedFrameId !== -1" - :readOnly="true" - :unifiedFrameId="unifiedFrameId" - :forceRefresh="forceRefresh" - @refresh-entries-list="refreshEntriesList" - /> - <div v-else class="h-100"> - Brak ramy do wyświetlenia - </div> - </div> - <div class="col h-100 pl-1 pt-0 pb-0 overflow-auto" id="frame-preview-right-pane"> - <unification-switchable-list - @unified-frame-selected="unifiedFrameSelected" - /> - </div> - </div> - ` -}; - Object.assign(LexicalUnitEdit, { props: { unifiedFrameId: Number, @@ -77,13 +21,14 @@ Object.assign(LexicalUnitEdit, { data() { return { gettext: window.gettext, + LexicalUnitEdit: LexicalUnitEdit, unified_frame: {}, unified_frame_title: '', unified_frame_arguments: [], active_unified_frame_argument: null, slowal_frames2selecional_preferencies_mapping: {}, lexical_units: [], - img_prefix: String, + img_prefix: window.STATIC_URL, frames: [], right_pane_tabs: [ {id: 'schemata', label: gettext('Schematy')}, @@ -109,7 +54,7 @@ Object.assign(LexicalUnitEdit, { hidden_frames: [], } }, - components: {InfoTooltip, Spinner, FramePreview, SlowalFrameComponent, ExamplesComponent, SemanticsSchemataComponent, MeaningComponent}, + components: {InfoTooltip, Spinner, UnificationFramePreview, SlowalFrameComponent, ExamplesComponent, SemanticsSchemataComponent, MeaningComponent}, emits: ['goToDisplay', 'refresh', 'swapFrames', 'refreshEntriesList', 'clearUnifiedFrameView'], watch: { forceRefresh(newVal, oldVal) { @@ -925,8 +870,13 @@ Object.assign(LexicalUnitEdit, { minSize: 10, }); } - }, - template: ` + } +}); + +export default LexicalUnitEdit; +</script> + +<template> <div class="col h-100 px-0 pt-0 pb-0 overflow-auto" id="semantics-frames-pane"> <div :id="'semantics-unified-frame-pane' + (readOnly ? '-preview' : '')" class="col w-100 p-0 overflow-auto"> <table v-if="!readOnly && !isReadOnlyForSuperLeksykograf()" class="table-button-menu sticky-top" cellspacing="1"> @@ -1178,8 +1128,9 @@ Object.assign(LexicalUnitEdit, { /> </div> <div v-if="right_pane_tab === 'frame_preview'" class="overflow-hidden" style="height: calc(100% - 43px)"> - <frame-preview - :key="currentPreviewedUnifiedFrameId" + <unification-frame-preview + :key="currentPreviewedUnifiedFrameId" + :lexicalUnitEditComponent="LexicalUnitEdit" :initialUnifiedFrameId="currentPreviewedUnifiedFrameId" @change-frame="changePreviewedUnifiedFrameId" @change-preview-to-edit="swapUnifiedFrames" @@ -1187,7 +1138,4 @@ Object.assign(LexicalUnitEdit, { </div> <div :class="right_pane_tab !== 'notes' && 'd-none'" id="notes-component"></div> </div> - ` -}); - -export default LexicalUnitEdit; +</template> diff --git a/entries/static/entries/js/selectional_preference.js b/frontend/src/components/unification/Unification/SelectionalPreference.js similarity index 100% rename from entries/static/entries/js/selectional_preference.js rename to frontend/src/components/unification/Unification/SelectionalPreference.js diff --git a/entries/static/entries/js/components/UnificationComponent.js b/frontend/src/components/unification/Unification/Unification.vue similarity index 56% rename from entries/static/entries/js/components/UnificationComponent.js rename to frontend/src/components/unification/Unification/Unification.vue index 5a808084643df85eab672120fb06b095310a8df1..926824132d8e764fd7a0e554ff4c370be9639133 100644 --- a/entries/static/entries/js/components/UnificationComponent.js +++ b/frontend/src/components/unification/Unification/Unification.vue @@ -1,5 +1,6 @@ -import UnificationSwitchableList from "./UnificationSwitchableList.js"; -import UnificationRightPane from "./UnificationRightPane.js"; +<script> +import UnificationSwitchableList from "./UnificationSwitchableList.vue"; +import UnificationRightPane from "./UnificationRightPane.vue"; export default { data () { @@ -7,7 +8,6 @@ export default { entryId: null, lexicalUnitId: null, unifiedFrameId: null, - isEdit: false, gettext: window.gettext, unificationEntriesListRefreshKey: 1, }; @@ -17,10 +17,8 @@ export default { lexicalUnitSelected (entryId, lexicalUnitId) { this.entryId = entryId; this.lexicalUnitId = lexicalUnitId; - this.isEdit = false; }, unifiedFrameSelected (unifiedFrameId, entryId, lexicalUnitId) { - this.isEdit = true; this.unifiedFrameId = unifiedFrameId; this.entryId = entryId; this.lexicalUnitId = lexicalUnitId; @@ -50,27 +48,29 @@ export default { }, }); }, - template: ` - <div id="entries-list" class="col h-100 w-100 px-0 overflow-hidden"> - <div id="entries-list-div" class="col p-0 h-100 w-100 overflow-hidden"> - <unification-switchable-list - :unificationEntriesListRefreshKey="unificationEntriesListRefreshKey" - :initialLexicalUnitId="lexicalUnitId ? lexicalUnitId : initialLexicalUnitId" - :initialEntryId="entryId ? entryId : initialEntryId" - @lexical-unit-selected="lexicalUnitSelected" - @unified-frame-selected="unifiedFrameSelected" - /> - </div> - </div> - <div id="entry-display" class="col h-100 p-0 overflow-hidden"> - <unification-right-pane - ref="unificationRightPane" - :entryId="entryId" - :lexicalUnitId="lexicalUnitId" - :initialUnifiedFrameId="unifiedFrameId" - :initialIsEdit="isEdit" - @refresh-entries-list="refreshEntriesList" - /> - </div> - ` }; +</script> + +<template> + <div id="entries-list" class="col h-100 w-100 pr-0 overflow-hidden"> + <div id="entries-list-div" class="col p-0 h-100 w-100 overflow-hidden"> + <unification-switchable-list + :unificationEntriesListRefreshKey="unificationEntriesListRefreshKey" + :initialLexicalUnitId="lexicalUnitId ? lexicalUnitId : initialLexicalUnitId" + :initialEntryId="entryId ? entryId : initialEntryId" + @lexical-unit-selected="lexicalUnitSelected" + @unified-frame-selected="unifiedFrameSelected" + /> + </div> + </div> + <div id="entry-display" class="col h-100 p-0 overflow-hidden"> + <unification-right-pane + ref="unificationRightPane" + :entryId="entryId" + :lexicalUnitId="lexicalUnitId" + :initialUnifiedFrameId="unifiedFrameId" + @refresh-entries-list="refreshEntriesList" + /> + </div> +</template> + diff --git a/entries/static/entries/js/components/UnificationEntriesForFramesList.js b/frontend/src/components/unification/Unification/UnificationEntriesForFramesList.vue similarity index 81% rename from entries/static/entries/js/components/UnificationEntriesForFramesList.js rename to frontend/src/components/unification/Unification/UnificationEntriesForFramesList.vue index 07d5f00451df7e1854acb20a5cd3d059d843faa0..a97c2ebab7f1890afefc879d3f0e3b195854ad1a 100644 --- a/entries/static/entries/js/components/UnificationEntriesForFramesList.js +++ b/frontend/src/components/unification/Unification/UnificationEntriesForFramesList.vue @@ -1,10 +1,11 @@ +<script> export default { props: { initialLexicalUnitId: Number, initialEntryId: Number, unificationEntriesListRefreshKey: Number, }, - data () { + data() { return { gettext: window.gettext, canViewAssignment: has_permission("users.view_assignment") @@ -16,22 +17,29 @@ export default { // this.datatableObject.ajax.reload(); setup_entries_for_frames_list({ table: this.$refs.table, - lexicalUnitSelected: (lexicalUnitUnifiedFrameId, entryId, lexicalUnitId) => { this.$emit('unifiedFrameSelected', lexicalUnitUnifiedFrameId, entryId, lexicalUnitId); }, + lexicalUnitSelected: (lexicalUnitUnifiedFrameId, entryId, lexicalUnitId) => { + this.$emit('unifiedFrameSelected', lexicalUnitUnifiedFrameId, entryId, lexicalUnitId); + }, selectEntryId: this.initialEntryId, secondarySelectEntryId: this.initialLexicalUnitId }); } }, emits: ['unifiedFrameSelected'], - mounted () { + mounted() { setup_entries_for_frames_list({ table: this.$refs.table, - lexicalUnitSelected: (lexicalUnitUnifiedFrameId, entryId, lexicalUnitId) => { this.$emit('unifiedFrameSelected', lexicalUnitUnifiedFrameId, entryId, lexicalUnitId); }, + lexicalUnitSelected: (lexicalUnitUnifiedFrameId, entryId, lexicalUnitId) => { + this.$emit('unifiedFrameSelected', lexicalUnitUnifiedFrameId, entryId, lexicalUnitId); + }, selectEntryId: this.initialEntryId, secondarySelectEntryId: this.initialLexicalUnitId }); }, - template: ` +}; +</script> + +<template> <table ref="table" class="table table-sm text-dark"> <thead> <tr> @@ -45,5 +53,4 @@ export default { <tbody id="entries"> </tbody> </table> - ` -}; +</template> diff --git a/frontend/src/components/unification/Unification/UnificationFramePreview.vue b/frontend/src/components/unification/Unification/UnificationFramePreview.vue new file mode 100644 index 0000000000000000000000000000000000000000..a24365e280861cfc04f3a6a74874c46da659d292 --- /dev/null +++ b/frontend/src/components/unification/Unification/UnificationFramePreview.vue @@ -0,0 +1,61 @@ +<script> +import UnificationSwitchableList from './UnificationSwitchableList.vue'; + +export default { + props: { + initialUnifiedFrameId: Number, + initialLexicalUnitId: Number, + forceRefresh: Number, + lexicalUnitEditComponent: Object, + }, + data () { + return { + unifiedFrameId: this.initialUnifiedFrameId + }; + }, + components: {UnificationSwitchableList}, + emits: ['changeFrame', 'refreshEntriesList'], + methods: { + unifiedFrameSelected (unifiedFrameId) { + this.$emit('changeFrame', unifiedFrameId); + }, + refreshEntriesList() { + this.$emit('refreshEntriesList') + }, + }, + mounted () { + Split(['#frame-preview-left-pane', '#frame-preview-right-pane'], { + sizes: [60, 40], + minSize: 20, + gutterSize: 4, + elementStyle: (dimension, size, gutterSize) => { + return { + 'flex-basis': 'calc(' + size + '% - ' + gutterSize + 'px)' + } + }, + }); + } +}; +</script> + +<template> + <div class="row h-100 overflow-hidden"> + <div :key="unifiedFrameId" class="col h-100 pr-0 pt-0 pb-0 overflow-auto" id="frame-preview-left-pane"> + <component v-bind:is="lexicalUnitEditComponent" + v-if="unifiedFrameId !== -1" + :readOnly="true" + :unifiedFrameId="unifiedFrameId" + :forceRefresh="forceRefresh" + @refresh-entries-list="refreshEntriesList" + /> + <div v-else class="h-100"> + Brak ramy do wyświetlenia + </div> + </div> + <div class="col h-100 pl-1 pt-0 pb-0 overflow-auto" id="frame-preview-right-pane"> + <unification-switchable-list + @unified-frame-selected="unifiedFrameSelected" + /> + </div> + </div> +</template> diff --git a/frontend/src/components/unification/Unification/UnificationFramesList.vue b/frontend/src/components/unification/Unification/UnificationFramesList.vue new file mode 100644 index 0000000000000000000000000000000000000000..b4e1bb451827a7b55dc90d980e0de3a5fbff6034 --- /dev/null +++ b/frontend/src/components/unification/Unification/UnificationFramesList.vue @@ -0,0 +1,52 @@ +<script> +export default { + props: { + initialUnifiedFrameId: Number, + unificationEntriesListRefreshKey: Number, + }, + data() { + return { + gettext: window.gettext, + canViewAssignment: has_permission("users.view_assignment") + } + }, + watch: { + unificationEntriesListRefreshKey() { + // TODO: reload data and click in selected row + // this.datatableObject.ajax.reload(); + setup_frames_list({ + table: this.$refs.table, + unifiedFrameSelected: (unifiedFrameId) => { + this.$emit('unifiedFrameSelected', unifiedFrameId); + }, + selectEntryId: this.initialEntryId, + }); + } + }, + emits: ['unifiedFrameSelected'], + mounted() { + setup_frames_list({ + table: this.$refs.table, + unifiedFrameSelected: (unifiedFrameId) => { + this.$emit('unifiedFrameSelected', unifiedFrameId); + }, + selectEntryId: this.initialUnifiedFrameId, + }); + }, +}; +</script> + +<template> + <table ref="table" class="table table-sm table-hover text-dark"> + <thead> + <tr> + <th class="p-1">{{ gettext('Rama') }}</th> + <th class="p-1">{{ gettext('Status') }}</th> + <th v-if="canViewAssignment" class="p-1">{{ gettext('Leksykograf') }}</th> + <th class="p-1" hidden="true">{{ gettext('Id') }}</th> + </tr> + </thead> + <tbody id="entries"> + </tbody> + </table> +</template> diff --git a/frontend/src/components/unification/Unification/UnificationRightPane.vue b/frontend/src/components/unification/Unification/UnificationRightPane.vue new file mode 100644 index 0000000000000000000000000000000000000000..5247642dd82167ba2fb54349bb9d0122f9d42e45 --- /dev/null +++ b/frontend/src/components/unification/Unification/UnificationRightPane.vue @@ -0,0 +1,68 @@ +<script> +import LexicalUnitEdit from './LexicalUnitEdit.vue'; + +export default { + components: {LexicalUnitEdit}, + props: { + entryId: Number, + lexicalUnitId: Number, + initialUnifiedFrameId: Number, + }, + emits: ['refreshEntriesList'], + data() { + return this.getInitialData(); + }, + methods: { + getInitialData() { + return { + key: this.lexicalUnitId, + entryIdLocal: this.entryId, + unifiedFrameId: this.initialUnifiedFrameId, + previewedUnifiedFrameId: null + }; + }, + goToDisplay() { + this.unifiedFrameId = null; + }, + refresh() { + this.key = null; + setTimeout(() => { + this.key = this.lexicalUnitId; + }, 0); + }, + swapFrames(previewedUnifiedFrameId) { + this.previewedUnifiedFrameId = this.unifiedFrameId; + this.unifiedFrameId = previewedUnifiedFrameId; + this.refresh(); + }, + refreshEntriesList() { + this.$emit('refreshEntriesList'); + } + }, + watch: { + lexicalUnitId() { + Object.assign(this, this.getInitialData()); + }, + initialUnifiedFrameId() { + Object.assign(this, this.getInitialData()); + } + }, +}; +</script> + +<template> + <div v-if="key || unifiedFrameId" :key="(key, entryIdLocal, unifiedFrameId)" class="row h-100 m-0 p-0 overflow-auto" id="semantics-top-pane"> + <lexical-unit-edit + ref="lexicalUnitEdit" + v-if="unifiedFrameId" + :key="unifiedFrameId" + :readOnly="false" + :unifiedFrameId="unifiedFrameId" + :previewedUnifiedFrameId="previewedUnifiedFrameId" + :initialRightPaneTab="previewedUnifiedFrameId && unifiedFrameId !== previewedUnifiedFrameId ? 'frame_preview' : 'schemata'" + @go-to-display="goToDisplay" + @swap-frames="swapFrames" + @refresh-entries-list="refreshEntriesList" + /> + </div> +</template> diff --git a/frontend/src/components/unification/Unification/UnificationSwitchableList.vue b/frontend/src/components/unification/Unification/UnificationSwitchableList.vue new file mode 100644 index 0000000000000000000000000000000000000000..68de141368ec852846985c5fa45c41bce67285bf --- /dev/null +++ b/frontend/src/components/unification/Unification/UnificationSwitchableList.vue @@ -0,0 +1,43 @@ +<script> +import UnificationEntriesForFramesList from "./UnificationEntriesForFramesList.vue"; +import UnificationEntriesList from "../Entries/EntriesList.vue"; +import UnificationFramesList from "./UnificationFramesList.vue"; + +export default { + props: { + initialLexicalUnitId: Number, + initialEntryId: Number, + unificationEntriesListRefreshKey: Number, + }, + data() { + return { + gettext: window.gettext, + isFrameView: false + } + }, + emits: ['lexicalUnitSelected', 'unifiedFrameSelected', 'refreshEntriesList'], + methods: { + lexicalUnitSelected(entryId, lexicalUnitId) { + this.$emit('lexicalUnitSelected', entryId, lexicalUnitId); + }, + unifiedFrameSelected(unifiedFrameId, entryId, lexicalUnitId) { + this.$emit('unifiedFrameSelected', unifiedFrameId, entryId, lexicalUnitId); + }, + }, + components: {UnificationEntriesList, UnificationEntriesForFramesList, UnificationFramesList}, +}; +</script> + +<template> + <label class="mt-2 position-absolute" style="z-index: 2"><input type="checkbox" v-model="isFrameView" /> {{ gettext('RAMY') }}</label> + <div v-if="!isFrameView" class="h-100"><unification-entries-for-frames-list + :unificationEntriesListRefreshKey="unificationEntriesListRefreshKey" + :initialLexicalUnitId="initialLexicalUnitId" + :initialEntryId="initialEntryId" + @unified-frame-selected="unifiedFrameSelected" + /></div> + <div v-else class="h-100"><unification-frames-list + :unificationEntriesListRefreshKey="unificationEntriesListRefreshKey" + @unified-frame-selected="unifiedFrameSelected" + /></div> +</template> diff --git a/entries/static/entries/js/components/LexicalUnitDisplay.js b/frontend/src/components/unification/shared/LexicalUnitDisplay.vue similarity index 98% rename from entries/static/entries/js/components/LexicalUnitDisplay.js rename to frontend/src/components/unification/shared/LexicalUnitDisplay.vue index d4d5244665f9e649fcac216ef6831e4b8d96b527..1fcd3094dd1ea1ecc30fc838d004abd157d34b36 100644 --- a/entries/static/entries/js/components/LexicalUnitDisplay.js +++ b/frontend/src/components/unification/shared/LexicalUnitDisplay.vue @@ -1,9 +1,9 @@ -import Spinner from './Spinner.js'; -import SemanticsSchemataComponent from "./frame-components/SemanticsSchemataComponent.js"; -import ExamplesComponent from "./frame-components/ExamplesComponent.js"; -import SlowalFrameComponent from "./frame-components/SlowalFrameComponent.js"; -import MeaningComponent from "./frame-components/MeaningComponent.js"; - +<script> +import Spinner from '/src/components/shared/Spinner.vue'; +import SemanticsSchemataComponent from "./frame-components/SemanticsSchemataComponent.vue"; +import ExamplesComponent from "./frame-components/ExamplesComponent.vue"; +import SlowalFrameComponent from "./frame-components/SlowalFrameComponent.vue"; +import MeaningComponent from "./frame-components/MeaningComponent.vue"; export default { components: { Spinner, SemanticsSchemataComponent, ExamplesComponent, SlowalFrameComponent, MeaningComponent }, @@ -184,7 +184,10 @@ export default { }); this.setup(); }, - template: ` +}; +</script> + +<template> <div class="col p-0 h-100 overflow-hidden"> <div id="main-frames-pane" class="row"> <div class="col h-100 pl-3 pr-1 pt-0 pb-2 overflow-auto" id="semantics-frames-pane"> @@ -286,5 +289,4 @@ export default { </div> </div> </div> - ` -} +</template> diff --git a/frontend/src/components/unification/shared/frame-components/ExamplesComponent.vue b/frontend/src/components/unification/shared/frame-components/ExamplesComponent.vue new file mode 100644 index 0000000000000000000000000000000000000000..8327a47583a297a049600290da0d0926b63c25e9 --- /dev/null +++ b/frontend/src/components/unification/shared/frame-components/ExamplesComponent.vue @@ -0,0 +1,90 @@ +<script> +import InfoTooltip from "/src/components/shared/InfoTooltip.vue"; + +export default { + props: { + examples: Object, + frame: Object, + frame_arguments: Object, + frame_arguments_or_type: null, + schemas: Object, + lus: Object, + }, + components: { InfoTooltip }, + data() { + return { + img_prefix: window.STATIC_URL + } + }, + emits: ['exampleSelected'], + methods: { + getExamples() { + let ret = this.examples; + if (this.schemas && this.schemas.length > 0) { + // ograniczone do schematu + ret = ret.filter(e => this.schemas.every(a => e.schema_ids.includes(parseInt(a.id)))); + } + if (this.frame_arguments && this.frame_arguments.length > 0) { + // ograniczone do argumentu ramy + if (this.frame_arguments_or_type) { + ret = ret.filter(e => this.frame_arguments.some(a => e.argument_ids.includes(a.id))); + } else { + ret = ret.filter(e => this.frame_arguments.every(a => e.argument_ids.includes(a.id))); + } + } + if (this.frame) { + ret = ret.filter(e => e.frame_ids.includes(this.frame.id)); + } + if (this.lus && this.lus.length > 0) { + ret = ret.filter(e => this.lus.every(lu => e.lu_ids.includes(lu.id))); + } + return ret; + }, + getSchemaStr(schema) { + return schema.positions.map(e => e.phrases.map(p => p.str).join(",")).join('|'); + }, + selectExample(example) { + example.selected = !example.selected; + this.$emit('exampleSelected', this.examples.filter(example => example.selected)); + } + }, + mounted() { + this.img_prefix = window.STATIC_URL; + }, +} +</script> + +<template> + <table id="semantics-examples" v-if="getExamples().length > 0" class="table table-sm table-hover" style=""> + <thead> + <tr> + <th scope="col">Przykład + <i v-if="frame_arguments" v-for="frame_argument in frame_arguments"> + <span class="example-role"> {{ ' ' }} + <span :class="frame_argument.role">{{ frame_argument.role }}</span> + </span> + </i> + <i v-if="lus" v-for="lu in lus">{{ ' ' + lu.str }}</i> + <i v-if="schemas" v-for="schema in schemas">{{ ' ' + getSchemaStr(schema) }}</i> + </th> + <th scope="col">Źródło</th> + <th scope="col">Opinia</th> + </tr> + </thead> + <tbody id="semantics-examples-list"> + <template v-for="example in getExamples()"> + <tr class="example" @mouseenter="example.hover = true" @mouseleave="example.hover = false" + @click.stop="selectExample(example)" + :class="example.selected ? 'active table-primary' : example.hover ? 'bg-highlight' : ''"> + <td class="py-1"> + {{ example.sentence }} + <info-tooltip v-if="example.note" :text="example.note" /> + </td> + <td class="py-1">{{ example.source }}</td> + <td class="py-1">{{ example.opinion }}</td> + </tr> + </template> + </tbody> + </table> + <p v-else class="mx-1 my-1" id="semantics-no-examples" style="display: none;">Brak przykładów</p> +</template> diff --git a/entries/static/entries/js/components/frame-components/MeaningComponent.js b/frontend/src/components/unification/shared/frame-components/MeaningComponent.vue similarity index 84% rename from entries/static/entries/js/components/frame-components/MeaningComponent.js rename to frontend/src/components/unification/shared/frame-components/MeaningComponent.vue index d497ec18e0fef485cd0b5174434eea6762305579..0576d023cf163864af59f8cbe4b0962419ae05f3 100644 --- a/entries/static/entries/js/components/frame-components/MeaningComponent.js +++ b/frontend/src/components/unification/shared/frame-components/MeaningComponent.vue @@ -1,4 +1,5 @@ -import InfoTooltip from "../InfoTooltip.js"; +<script> +import InfoTooltip from "/src/components/shared/InfoTooltip.vue"; export default { props: { @@ -6,14 +7,14 @@ export default { selectedExamples: Object }, emits: ['meaningLuSelected'], - data () { + data() { return { iconUrl: window.STATIC_URL + 'common/img/ext-link.svg' } }, components: {InfoTooltip}, methods: { - getTooltipStr (lu) { + getTooltipStr(lu) { const tooltip = []; if (lu.definition) { tooltip.push(lu.definition); @@ -31,20 +32,22 @@ export default { this.$emit('meaningLuSelected', this.lexicalUnits.filter(lexicalUnit => lexicalUnit.selected)); } }, - template: ` +}; +</script> + +<template> <p class="mb-1"> <template v-for="lexicalUnit in lexicalUnits"> <span @mouseenter="lexicalUnit.hover=true" @mouseleave="lexicalUnit.hover=false" @click.stop="select(lexicalUnit)" - :class="lexicalUnit.selected ? 'entry-meaning active' : lexicalUnit.hover ? 'entry-meaning active' : ''" - class="lexical-unit entry-meaning" style="padding-left: 4px; padding-right: 4px;">{{lexicalUnit.str}}</span> + :class="lexicalUnit.selected ? 'entry-meaning active' : lexicalUnit.hover ? 'entry-meaning active' : ''" + class="lexical-unit entry-meaning" style="padding-left: 4px; padding-right: 4px;">{{lexicalUnit.str}}</span> <info-tooltip v-if="getTooltipStr(lexicalUnit)" :text="getTooltipStr(lexicalUnit)"/> <a v-if="lexicalUnit.url" class="lu-plwn" style="padding-left: 4px;" :href="lexicalUnit.url" target="_blank"> <img :src="iconUrl" alt="external link" height="14"> </a> </template> </p> - ` -} +</template> diff --git a/frontend/src/components/unification/shared/frame-components/SemanticsSchemataComponent.vue b/frontend/src/components/unification/shared/frame-components/SemanticsSchemataComponent.vue new file mode 100644 index 0000000000000000000000000000000000000000..b6bfb59cfb59c49b8ebb222b6751e65c01a6b70a --- /dev/null +++ b/frontend/src/components/unification/shared/frame-components/SemanticsSchemataComponent.vue @@ -0,0 +1,174 @@ +<script> +import InfoTooltip from "/src/components/shared/InfoTooltip.vue"; + +export default { + props: { + subentries: Object, + frame: Object, + alternations: Object, + realisation_phrases: Object, + realisation_descriptions: Object, + selectedExamples: Object + }, + components: {InfoTooltip}, + emits: ['schemataSelected'], + data() { + return { + img_prefix: window.STATIC_URL + } + }, + methods: { + getFunctions(position) { + const props_spans = []; + if (position.func.str !== '') { + props_spans.push({str: position.func.str, tooltip: position.func.desc}); + } + if (position.control.str !== '') { + props_spans.push({str: position.control.str, tooltip: position.control.desc}); + } + if (position.p_control.str !== '') { + props_spans.push({str: position.p_control.str, tooltip: position.p_control.desc}); + } + return props_spans; + }, + getSchemataPositionCnt(schema) { + return schema.positions.length; + }, + getRealisationDescriptions(schema) { + const alternationDescList = []; + if (this.alternations) { + const curr_alternations = this.alternations[this.frame.id][schema.id]; + const curr_realisation_descriptions = this.realisation_descriptions[this.frame.id][schema.id]; + for (let i in curr_alternations) { + alternationDescList.push(curr_realisation_descriptions[i]); + } + } + return '<i>' + alternationDescList + '</i>'; + }, + getPhraseCss(schema, position) { + const styles = []; + if (this.alternations) { + const argumentIdSet = new Set(); + + const curr_alternations = this.alternations[this.frame.id][schema.id]; + for (let i in curr_alternations) { + const alternation = curr_alternations[i] + + for (let arg_id in alternation) { + const phrase_ids = alternation[arg_id]; + phrase_ids.forEach(phrase_id => { + if (phrase_id.startsWith(position.id)) { + argumentIdSet.add(arg_id); + } + }); + } + } + + argumentIdSet.forEach(argumentId => { + const argument = this.frame.arguments.find(arg => argumentId.endsWith(arg.argument_id)); + const role = argument.role; + styles.push(role); + }); + + } + const selectedExampleFrameArguments = this.selectedExamples && this.selectedExamples.length > 0 ? new Set(this.selectedExamples.map(e => e.positions).flat()) : null; + + if (selectedExampleFrameArguments != null) { + styles.push(selectedExampleFrameArguments.has(position.id) ? 'example-yes' : 'example-no'); + } + return styles; + }, + getPositionPhrases(schema, position) { + const phrases = []; + if (this.alternations) { + const curr_alternations = this.alternations[this.frame.id][schema.id]; + for (let i in curr_alternations) { + const alternation = curr_alternations[i] + + for (let arg_id in alternation) { + const phrase_ids = alternation[arg_id]; + phrase_ids.forEach(phrase_id => { + if (phrase_id.startsWith(position.id)) { + phrases.push(this.realisation_phrases[arg_id][i][phrase_id]); + } + }); + } + } + } + return phrases; + }, + selectSchema(schema) { + schema.selected = !schema.selected; + const selected = []; + this.subentries.forEach(subentry => { + subentry.schemata.forEach(s => { + if (s.selected) { + selected.push(s); + } + }); + }); + this.$emit('schemataSelected', selected); + } + }, + mounted() { + this.img_prefix = window.STATIC_URL; + }, +}; +</script> + +<template> + <div> + <template v-for="subentry in subentries"> + <div class="subentry"> + <div class="mb-1 sticky-top"><h5 class="bg-dark text-light p-1">{{subentry.str}}</h5></div> + <template v-for="schema in subentry.schemata"> + <div class="schema mb-3" + v-if="alternations[this.frame.id][schema.id]" + @mouseenter="schema.hover=true" + @mouseleave="schema.hover=false" + @click="selectSchema(schema)" + :class="(schema.selected ? 'active' : schema.hover ? 'bg-highlight' : '')" + > + <table class="table m-0 table-borderless border border-secondary text-dark"> + <tbody> + <tr class="opinion-row"> + <th scope="row" class="py-2 px-1 text-secondary" style="width: 3em;">Opinia</th> + <td class="opinion-cell py-2 px-1" :colspan="getSchemataPositionCnt(schema)"><img + :src="img_prefix + 'entries/img/' + schema.opinion_key + '.svg'" width="12" + height="12" :alt="schema.opinion"> {{schema.opinion}} + </td> + </tr> + + <tr> + <th scope="row" class="py-2 px-1 text-secondary">Funkcja</th> + + <td class="position py-2 px-1 border-top border-left border-secondary" + v-for="position in schema.positions"> + <div v-for="f in getFunctions(position)" class="phrase px-1 py-2"> + <info-tooltip :text="f.tooltip" :visibleText="f.str"/> + </div> + </td> + + </tr> + + <tr class="realisation-description"> + <td class="px-1 py-2" :colspan="getSchemataPositionCnt(schema)" v-html="getRealisationDescriptions(schema)"></td> + </tr> + <tr class="phrase-types alt-0"> + <th scope="row" class="py-0 px-1 text-secondary">Typy fraz</th> + <td v-for="position in schema.positions" class="px-0 py-0 border-top border-left border-secondary"> + <div v-for="phrase in position.phrases" class="phrase px-1 py-2" + :class="getPhraseCss(schema, position)"> + <info-tooltip :text="phrase.desc" :visibleText="phrase.str"/> + </div> + <div v-for="phrase in getPositionPhrases(schema, position)" class="realisation-phrase px-1 py-2"><i>{{phrase}}</i></div> + </td> + </tr> + </tbody> + </table> + </div> + </template> + </div> + </template> + </div> +</template> diff --git a/entries/static/entries/js/components/frame-components/SlowalFrameComponent.js b/frontend/src/components/unification/shared/frame-components/SlowalFrameComponent.vue similarity index 60% rename from entries/static/entries/js/components/frame-components/SlowalFrameComponent.js rename to frontend/src/components/unification/shared/frame-components/SlowalFrameComponent.vue index f7fec2a7420604ef9d85479e6ce01fa8b9164dce..88361c58740e99354d1eed2797eab543f702853e 100644 --- a/entries/static/entries/js/components/frame-components/SlowalFrameComponent.js +++ b/frontend/src/components/unification/shared/frame-components/SlowalFrameComponent.vue @@ -1,43 +1,47 @@ -import InfoTooltip from "../InfoTooltip.js"; +<script> +import InfoTooltip from "/src/components/shared/InfoTooltip.vue"; export default { - props: { - frame: Object, - selectedExamples: Object + props: { + frame: Object, + selectedExamples: Object + }, + components: {InfoTooltip}, + emits: ['frameSelectionChanged'], + data() { + return { + img_prefix: window.STATIC_URL, + } + }, + methods: { + getTitleHTML() { + const ret = window.lexical_units2dom(this.frame.lexical_units); + return ret; }, - components: {InfoTooltip}, - emits: ['frameSelectionChanged'], - data() { - return { - img_prefix: String, - } + getOpinionHTML() { + return window.make_opinion_row(this.frame, this.frame.arguments.length, 3).outerHTML; }, - methods: { - getTitleHTML() { - const ret = window.lexical_units2dom(this.frame.lexical_units); - return ret; - }, - getOpinionHTML() { - return window.make_opinion_row(this.frame, this.frame.arguments.length, 3).outerHTML; - }, - getArguments() { - return this.frame.arguments; - }, - selectArgument(argument) { - argument.selected = !argument.selected; - const selectedArguments = this.frame.arguments.filter(argument => argument.selected) - this.$emit('frameSelectionChanged', selectedArguments); - }, - computeArgumentCSS(argument) { - const selectedExampleFrameArguments = this.selectedExamples && this.selectedExamples.length > 0 ? new Set(this.selectedExamples.map(e => e.argument_ids).flat()) : null; - return argument.role + ' ' + (argument.selected ? 'active' : argument.hover ? 'bg-highlight' : '') - + (selectedExampleFrameArguments != null ? selectedExampleFrameArguments.has(argument.id) ? 'example-yes' : 'example-no' : ''); - } + getArguments() { + return this.frame.arguments; }, - mounted () { - this.img_prefix = window.STATIC_URL; + selectArgument(argument) { + argument.selected = !argument.selected; + const selectedArguments = this.frame.arguments.filter(argument => argument.selected) + this.$emit('frameSelectionChanged', selectedArguments); }, - template: ` + computeArgumentCSS(argument) { + const selectedExampleFrameArguments = this.selectedExamples && this.selectedExamples.length > 0 ? new Set(this.selectedExamples.map(e => e.argument_ids).flat()) : null; + return argument.role + ' ' + (argument.selected ? 'active' : argument.hover ? 'bg-highlight' : '') + + (selectedExampleFrameArguments != null ? selectedExampleFrameArguments.has(argument.id) ? 'example-yes' : 'example-no' : ''); + } + }, + mounted() { + this.img_prefix = window.STATIC_URL; + }, +}; +</script> + +<template> <table class="table m-0 table-borderless border border-secondary text-dark"> <tbody> <tr class="opinion-row" v-html="getOpinionHTML()"> @@ -77,7 +81,4 @@ export default { </tr> </tbody> </table> - ` -} - - +</template> diff --git a/frontend/src/main.js b/frontend/src/main.js index eb8f249b7a1f075cf3f98c3d0ae663d8144af065..f0fbbbc5d721560d7c8e27ab8478693c56b03d01 100644 --- a/frontend/src/main.js +++ b/frontend/src/main.js @@ -3,8 +3,8 @@ import './style.css' import App from './App.vue' import { createRouter, createWebHistory } from "vue-router"; -import Entries from "./components/Entries.vue"; -import Unification from "./components/Unification.vue"; +import Entries from "./components/unification/Entries/Entries.vue"; +import Unification from "./components/unification/Unification/Unification.vue"; const router = createRouter({ history: createWebHistory(), @@ -16,5 +16,12 @@ const router = createRouter({ }); const app = createApp(App); +let mounted = false; app.use(router); -app.mount('#vue-app'); + +window.update_entries = function () { + if (!mounted) { + app.mount('#vue-app'); + mounted = true; + } +} diff --git a/frontend/vite.config.js b/frontend/vite.config.js index 5ab96ec10304479c1e992056f7af78d487fab5c7..2c0cdf08f68fc0441cf964e57ad702a951325775 100644 --- a/frontend/vite.config.js +++ b/frontend/vite.config.js @@ -5,6 +5,11 @@ import vue from '@vitejs/plugin-vue' // https://vitejs.dev/config/ export default defineConfig({ plugins: [vue()], + resolve: { + alias: { + '/src': resolve(__dirname, './src'), + }, + }, base: '/static/', server: { host: '0.0.0.0', diff --git a/phrase_expansions/management/commands/import_expansions.py b/phrase_expansions/management/commands/import_expansions.py index ebf2c08fbd24a55da7b5dbe4b5a11f7cd3a447c2..85b3ca7cdf7430a2c1b4c072aaec2a9ec53a8117 100644 --- a/phrase_expansions/management/commands/import_expansions.py +++ b/phrase_expansions/management/commands/import_expansions.py @@ -38,8 +38,8 @@ def import_expansions(): expansions = parser.getContentHandler()._expansions - for cls in (ExpansionOpinion, PhraseExpansion, ExpansionPosition, ExpansionPhrase, ExpansionPhraseDescription): - cls.objects.all().delete() + # for cls in (ExpansionOpinion, PhraseExpansion, ExpansionPosition, ExpansionPhrase, ExpansionPhraseDescription): + # cls.objects.all().delete() opinions = [(50, u'col'), (40, u'dat'), (20, u'unc'), (10, u'cer'),] for pri, short in opinions: diff --git a/syntax/management/commands/import_tei.py b/syntax/management/commands/import_tei.py index 0f78622ae773bd7864a4b6c196514ae3c3ea6103..e936e5d538f7ff23613928a4b4fbad37b7732119 100644 --- a/syntax/management/commands/import_tei.py +++ b/syntax/management/commands/import_tei.py @@ -36,7 +36,7 @@ def import_tei(): #xml_file = os.path.join(BASE_DIR, 'data', 'walenty', 'walenty_20200926_smaller.xml') xml_file = os.path.join(BASE_DIR, 'data', 'walenty', 'walenty_20210913_smaller.xml') # xml_file = os.path.join(BASE_DIR, 'data', 'walenty', 'walenty_20210913_smallest.xml') - # xml_file = os.path.join(BASE_DIR, 'data', 'walenty', 'walenty_20210913.xml') + xml_file = os.path.join(BASE_DIR, 'data', 'walenty', 'walenty_20210913.xml') xml_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), xml_file)