[IMP] mrp{,_subcontracting}: OWL adaptations

Adapt event handling to better match OWL specifications.

closes odoo/odoo#105067

X-original-commit: 5c1701de318284bd13a75cab221bc49e4ef4a52d
Signed-off-by: William Henrotin (whe) <whe@odoo.com>
This commit is contained in:
clesgow
2022-11-07 09:12:12 +01:00
parent 71bb676575
commit 6b9a443f7c
17 changed files with 73 additions and 133 deletions
@@ -5,7 +5,7 @@ import { useService } from "@web/core/utils/hooks";
import { BomOverviewControlPanel } from "../bom_overview_control_panel/mrp_bom_overview_control_panel";
import { BomOverviewTable } from "../bom_overview_table/mrp_bom_overview_table";
const { Component, EventBus, onMounted, onWillStart, onWillUnmount, useState } = owl;
const { Component, EventBus, onWillStart, useSubEnv, useState } = owl;
export class BomOverviewComponent extends Component {
setup() {
@@ -35,28 +35,14 @@ export class BomOverviewComponent extends Component {
bomQuantity: null,
});
useSubEnv({
overviewBus: new EventBus(),
});
onWillStart(async () => {
await this.getWarehouses();
await this.initBomData();
});
onMounted(() => {
this.bus.addEventListener("change-fold", (ev) => this._onChangeFolded(ev.detail));
this.bus.addEventListener("change-display", (ev) => this._onChangeDisplay(ev.detail));
this.bus.addEventListener("change-quantity", (ev) => this._onChangeBomQuantity(ev.detail));
this.bus.addEventListener("change-variant", (ev) => this._onChangeVariant(ev.detail));
this.bus.addEventListener("change-warehouse", (ev) => this._onChangeWarehouse(ev.detail));
this.bus.addEventListener("print", (ev) => this._onClickPrint(ev.detail));
});
onWillUnmount(() => {
this.bus.removeEventListener("change-fold", (ev) => this._onChangeFolded(ev.detail));
this.bus.removeEventListener("change-display", (ev) => this._onChangeDisplay(ev.detail));
this.bus.removeEventListener("change-quantity", (ev) => this._onChangeBomQuantity(ev.detail));
this.bus.removeEventListener("change-variant", (ev) => this._onChangeVariant(ev.detail));
this.bus.removeEventListener("change-warehouse", (ev) => this._onChangeWarehouse(ev.detail));
this.bus.removeEventListener("print", (ev) => this._onClickPrint(ev.detail));
});
}
//---- Data ----
@@ -102,39 +88,38 @@ export class BomOverviewComponent extends Component {
//---- Handlers ----
_onChangeFolded(foldInfo) {
onChangeFolded(foldInfo) {
const { ids, isFolded } = foldInfo;
const operation = isFolded ? "delete" : "add";
ids.forEach(id => this.unfoldedIds[operation](id));
}
_onChangeDisplay(displayInfo) {
const { type, value } = displayInfo;
this.state.showOptions[type] = value;
onChangeDisplay(displayInfo) {
this.state.showOptions[displayInfo] = !this.state.showOptions[displayInfo];
}
async _onChangeBomQuantity(newQuantity) {
async onChangeBomQuantity(newQuantity) {
if (this.state.bomQuantity != newQuantity) {
this.state.bomQuantity = newQuantity;
await this.getBomData();
}
}
async _onChangeVariant(variantId) {
async onChangeVariant(variantId) {
if (this.state.currentVariantId != variantId) {
this.state.currentVariantId = variantId;
await this.getBomData();
}
}
async _onChangeWarehouse(warehouseId) {
async onChangeWarehouse(warehouseId) {
if (this.state.currentWarehouse.id != warehouseId) {
this.state.currentWarehouse = this.warehouses.find(wh => wh.id == warehouseId);
await this.getBomData();
}
}
async _onClickPrint(printAll) {
async onClickPrint(printAll) {
return this.actionService.doAction({
type: "ir.actions.report",
report_type: "qweb-pdf",
@@ -3,21 +3,25 @@
<div t-name="mrp.BomOverviewComponent" class="o_action" owl="1">
<BomOverviewControlPanel
bus="bus"
bomQuantity="state.bomQuantity"
uomName="uomName"
variants="variants"
showOptions="state.showOptions"
showVariants="showVariants"
currentWarehouse="state.currentWarehouse"
warehouses="warehouses"/>
warehouses="warehouses"
print.bind="onClickPrint"
changeWarehouse.bind="onChangeWarehouse"
changeVariant.bind="onChangeVariant"
changeBomQuantity.bind="onChangeBomQuantity"
changeDisplay.bind="onChangeDisplay"/>
<BomOverviewTable
bus="bus"
uomName="uomName"
showOptions="state.showOptions"
currentWarehouseId="state.currentWarehouse.id"
data="state.bomData"/>
data="state.bomData"
changeFolded.bind="onChangeFolded"/>
</div>
</templates>
@@ -1,9 +1,10 @@
/** @odoo-module **/
import { useBus } from "@web/core/utils/hooks";
import { BomOverviewLine } from "../bom_overview_line/mrp_bom_overview_line";
import { BomOverviewExtraBlock } from "../bom_overview_extra_block/mrp_bom_overview_extra_block";
const { Component, onMounted, onWillUnmount, onWillUpdateProps, useState } = owl;
const { Component, onWillUnmount, onWillUpdateProps, useState } = owl;
export class BomOverviewComponentsBlock extends Component {
setup() {
@@ -13,15 +14,12 @@ export class BomOverviewComponentsBlock extends Component {
unfoldAll: this.props.unfoldAll || false,
});
if (this.props.unfoldAll) {
this.props.bus.trigger("change-fold", { ids: this.childIds, isFolded: false });
this.props.changeFolded({ ids: this.childIds, isFolded: false });
}
onMounted(() => {
if (this.hasComponents) {
this.props.bus.addEventListener(`toggle-fold-${this.identifier}`, (ev) => this._onToggleFolded(ev.detail));
this.props.bus.addEventListener("unfold-all", () => this._unfoldAll());
}
});
if (this.hasComponents) {
useBus(this.env.overviewBus, "unfold-all", () => this._unfoldAll());
}
onWillUpdateProps(newProps => {
if (this.data.product_id != newProps.data.product_id) {
@@ -34,26 +32,24 @@ export class BomOverviewComponentsBlock extends Component {
onWillUnmount(() => {
if (this.hasComponents) {
this.props.bus.trigger("change-fold", { ids: this.childIds, isFolded: true });
this.props.bus.removeEventListener(`toggle-fold-${this.identifier}`, (ev) => this._onToggleFolded(ev.detail));
this.props.bus.removeEventListener("unfold-all", () => this._unfoldAll());
this.props.changeFolded({ ids: this.childIds, isFolded: true });
}
});
}
//---- Handlers ----
_onToggleFolded(foldId) {
onToggleFolded(foldId) {
const newState = !this.state[foldId];
this.state[foldId] = newState;
this.state.unfoldAll = false;
this.props.bus.trigger("change-fold", { ids: [foldId], isFolded: newState });
this.props.changeFolded({ ids: [foldId], isFolded: newState });
}
_unfoldAll() {
const allChildIds = this.childIds;
this.state.unfoldAll = true;
allChildIds.forEach(id => this.state[id] = false);
this.props.bus.trigger("change-fold", { ids: allChildIds, isFolded: false });
this.props.changeFolded({ ids: allChildIds, isFolded: false });
}
//---- Getters ----
@@ -74,14 +70,6 @@ export class BomOverviewComponentsBlock extends Component {
return this.getIdentifier(this.data);
}
get operationsId() {
return this.getIdentifier(this.data, "operations");
}
get byproductsId() {
return this.getIdentifier(this.data, "byproducts");
}
get showOperations() {
return this.props.showOptions.operations;
}
@@ -104,11 +92,11 @@ BomOverviewComponentsBlock.components = {
BomOverviewExtraBlock,
};
BomOverviewComponentsBlock.props = {
bus: Object,
unfoldAll: { type: Boolean, optional: true },
showOptions: Object,
currentWarehouseId: { type: Number, optional: true },
data: Object,
changeFolded: Function,
};
BomOverviewComponentsBlock.defaultProps = {
unfoldAll: false,
@@ -5,37 +5,36 @@
<t name="components" t-if="hasComponents">
<t t-foreach="data.components" t-as="line" t-key="line.index">
<BomOverviewLine
bus="props.bus"
isFolded="state[getIdentifier(line)]"
parentId="identifier"
showOptions="props.showOptions"
data="line"/>
data="line"
toggleFolded.bind="onToggleFolded"/>
<t t-if="!state[getIdentifier(line)] &amp;&amp; hasComponents">
<BomOverviewComponentsBlock
bus="props.bus"
unfoldAll="state.unfoldAll"
showOptions="props.showOptions"
currentWarehouseId="props.currentWarehouseId"
data="line"/>
data="line"
changeFolded.bind="props.changeFolded"/>
</t>
</t>
</t>
<t name="operations" t-if="showOperations &amp;&amp; !!data.operations &amp;&amp; data.operations.length > 0">
<BomOverviewExtraBlock
bus="props.bus"
unfoldAll="state.unfoldAll"
type="'operations'"
showOptions="props.showOptions"
data="data"/>
data="data"
changeFolded.bind="props.changeFolded"/>
</t>
<t name="byproducts" t-if="!!data.byproducts &amp;&amp; data.byproducts.length > 0">
<BomOverviewExtraBlock
bus="props.bus"
unfoldAll="state.unfoldAll"
type="'byproducts'"
showOptions="props.showOptions"
data="data"/>
data="data"
changeFolded.bind="props.changeFolded"/>
</t>
</t>
@@ -18,7 +18,7 @@ export class BomOverviewControlPanel extends Component {
updateQuantity(ev) {
const newVal = isNaN(ev.target.value) ? 1 : parseInt(ev.target.value);
this.props.bus.trigger("change-quantity", newVal);
this.props.changeBomQuantity(newVal);
}
onKeyPress(ev) {
@@ -28,20 +28,8 @@ export class BomOverviewControlPanel extends Component {
}
}
changeVariant(ev) {
this.props.bus.trigger("change-variant", ev.target.value);
}
changeWarehouse(warehouseId) {
this.props.bus.trigger("change-warehouse", warehouseId);
}
clickPrint(printAll=false) {
this.props.bus.trigger("print", printAll);
}
clickUnfold() {
this.props.bus.trigger("unfold-all");
this.env.overviewBus.trigger("unfold-all");
}
}
@@ -53,7 +41,6 @@ BomOverviewControlPanel.components = {
BomOverviewDisplayFilter,
};
BomOverviewControlPanel.props = {
bus: Object,
bomQuantity: Number,
showOptions: Object,
showVariants: { type: Boolean, optional: true },
@@ -62,6 +49,11 @@ BomOverviewControlPanel.props = {
uomName: { type: String, optional: true },
currentWarehouse: Object,
warehouses: { type: Array, optional: true },
print: Function,
changeWarehouse: Function,
changeVariant: Function,
changeBomQuantity: Function,
changeDisplay: Function,
};
BomOverviewControlPanel.defaultProps = {
variants: {},
@@ -6,9 +6,9 @@
<t t-set-slot="control-panel-bottom-left-buttons">
<div class="o_cp_buttons">
<div class="o_list_buttons o_mrp_bom_report_buttons">
<button t-on-click="() => this.clickPrint()" type="button" class="btn btn-primary">Print</button>
<button t-on-click="() => this.props.print()" type="button" class="btn btn-primary">Print</button>
<t t-if="props.showVariants">
<button t-on-click="() => this.clickPrint(true)" type="button" class="btn btn-primary ms-1">Print All Variants</button>
<button t-on-click="() => this.props.print(true)" type="button" class="btn btn-primary ms-1">Print All Variants</button>
</t>
<button t-on-click="clickUnfold" type="button" class="btn btn-primary ms-1">Unfold</button>
</div>
@@ -30,7 +30,7 @@
<div t-if="props.showVariants" class="col-lg-11 row gx-1 mb-1">
<label class="col-xl-2 col-lg-3 col-sm-4">Variant:</label>
<div class="col-xl-10 col-lg-9 col-sm-8">
<select class="o_input" t-on-change="changeVariant">
<select class="o_input" t-on-change="(ev) => this.props.changeVariant(ev.target.value)">
<option t-foreach="props.variants" t-as="variant" t-att-value="variant" t-key="variant">
<t t-esc="props.variants[variant]"/>
</option>
@@ -49,13 +49,13 @@
<span class="fa fa-home"/> Warehouse: <span t-esc="props.currentWarehouse.name"/>
</t>
<t t-foreach="props.warehouses" t-as="wh" t-key="wh.id">
<DropdownItem onSelected="() => this.changeWarehouse(wh.id)" t-esc="wh.name"/>
<DropdownItem onSelected="() => this.props.changeWarehouse(wh.id)" t-esc="wh.name"/>
</t>
</Dropdown>
</t>
<BomOverviewDisplayFilter
bus="props.bus"
showOptions="props.showOptions"/>
showOptions="props.showOptions"
changeDisplay.bind="props.changeDisplay"/>
</div>
</t>
</ControlPanel>
@@ -13,11 +13,6 @@ export class BomOverviewDisplayFilter extends Component {
operations: this.env._t('Operations'),
};
}
//---- Handlers ----
onClickDisplay(optionKey) {
this.props.bus.trigger("change-display", { type: optionKey, value: !this.props.showOptions[optionKey] });
}
//---- Getters ----
@@ -36,7 +31,6 @@ BomOverviewDisplayFilter.components = {
DropdownItem,
}
BomOverviewDisplayFilter.props = {
bus: Object,
showOptions: {
type: Object,
shape: {
@@ -48,4 +42,5 @@ BomOverviewDisplayFilter.props = {
attachments: Boolean,
},
},
changeDisplay: Function,
};
@@ -8,7 +8,7 @@
Display: <span t-esc="currentDisplayedNames"/>
</t>
<t t-foreach="displayableOptions" t-as="optionKey" t-key="optionKey">
<DropdownItem parentClosingMode="'none'" class="{ o_menu_item: true, selected: this.props.showOptions[optionKey] }" onSelected="() => this.onClickDisplay(optionKey)" t-esc="displayOptions[optionKey]"/>
<DropdownItem parentClosingMode="'none'" class="{ o_menu_item: true, selected: props.showOptions[optionKey] }" onSelected="() => this.props.changeDisplay(optionKey)" t-esc="displayOptions[optionKey]"/>
</t>
</Dropdown>
</t>
@@ -1,9 +1,10 @@
/** @odoo-module **/
import { useBus } from "@web/core/utils/hooks";
import { BomOverviewLine } from "../bom_overview_line/mrp_bom_overview_line";
import { BomOverviewSpecialLine } from "../bom_overview_special_line/mrp_bom_overview_special_line";
const { Component, onMounted, onWillUnmount, onWillUpdateProps, useState } = owl;
const { Component, onWillUnmount, onWillUpdateProps, useState } = owl;
export class BomOverviewExtraBlock extends Component {
setup() {
@@ -11,13 +12,10 @@ export class BomOverviewExtraBlock extends Component {
isFolded: !this.props.unfoldAll,
});
if (this.props.unfoldAll) {
this.props.bus.trigger("change-fold", { ids: [this.identifier], isFolded: false });
this.props.changeFolded({ ids: [this.identifier], isFolded: false });
}
onMounted(() => {
this.props.bus.addEventListener(`toggle-fold-${this.identifier}`, () => this._onToggleFolded());
this.props.bus.addEventListener("unfold-all", () => this._unfold());
});
useBus(this.env.overviewBus, "unfold-all", () => this._unfold());
onWillUpdateProps(newProps => {
if (this.props.data.product_id != newProps.data.product_id) {
@@ -26,23 +24,22 @@ export class BomOverviewExtraBlock extends Component {
});
onWillUnmount(() => {
this.props.bus.trigger("change-fold", { ids: [this.identifier], isFolded: true });
this.props.bus.removeEventListener(`toggle-fold-${this.identifier}`, () => this._onToggleFolded());
this.props.bus.removeEventListener("unfold-all", () => this._unfold());
// Need to notify main component that the block was folded so it doesn't appear on the PDF.
this.changeFolded({ ids: [this.identifier], isFolded: true });
});
}
//---- Handlers ----
_onToggleFolded() {
onToggleFolded() {
const newState = !this.state.isFolded;
this.state.isFolded = newState;
this.props.bus.trigger("change-fold", { ids: [this.identifier], isFolded: newState });
this.props.changeFolded({ ids: [this.identifier], isFolded: newState });
}
_unfold() {
this.state.isFolded = false;
this.props.bus.trigger("change-fold", { ids: [this.identifier], isFolded: false });
this.props.changeFolded({ ids: [this.identifier], isFolded: false })
}
//---- Getters ----
@@ -58,7 +55,6 @@ BomOverviewExtraBlock.components = {
BomOverviewSpecialLine,
};
BomOverviewExtraBlock.props = {
bus: Object,
unfoldAll: { type: Boolean, optional: true },
type: {
type: String,
@@ -66,6 +62,7 @@ BomOverviewExtraBlock.props = {
},
showOptions: Object,
data: Object,
changeFolded: Function,
};
BomOverviewExtraBlock.defaultProps = {
showAvailabilities: false,
@@ -3,16 +3,14 @@
<t t-name="mrp.BomOverviewExtraBlock" owl="1">
<BomOverviewSpecialLine
bus="props.bus"
type="props.type"
isFolded="state.isFolded"
parentId="identifier"
showOptions="props.showOptions"
data="props.data"/>
data="props.data"
toggleFolded.bind="onToggleFolded"/>
<t t-if="!state.isFolded" t-foreach="props.type == 'operations' ? props.data.operations : props.data.byproducts" t-as="extra_data" t-key="extra_data.index">
<BomOverviewLine
bus="props.bus"
showOptions="props.showOptions"
data="extra_data"/>
</t>
@@ -63,12 +63,6 @@ export class BomOverviewLine extends Component {
});
}
onToggleFolded() {
if (this.props.parentId) {
this.props.bus.trigger(`toggle-fold-${this.props.parentId}`, this.identifier);
}
}
//---- Getters ----
get data() {
@@ -152,9 +146,7 @@ export class BomOverviewLine extends Component {
BomOverviewLine.template = "mrp.BomOverviewLine";
BomOverviewLine.props = {
bus: Object,
isFolded: { type: Boolean, optional: true },
parentId: { type: String, optional: true },
showOptions: {
type: Object,
shape: {
@@ -168,7 +160,9 @@ BomOverviewLine.props = {
},
currentWarehouseId: { type: Number, optional: true },
data: Object,
toggleFolded: { type: Function, optional: true },
};
BomOverviewLine.defaultProps = {
isFolded: true,
toggleFolded: () => {},
};
@@ -5,7 +5,7 @@
<td name="td_mrp_bom">
<div t-attf-style="margin-left: {{ marginMultiplicator * 20 }}px">
<t t-if="data.level > 0 &amp;&amp; hasComponents">
<button t-on-click="onToggleFolded" class="o_mrp_bom_unfoldable btn btn-light p-0" t-attf-aria-label="{{ props.isFolded ? 'Unfold' : 'Fold' }}" t-attf-title="{{ props.isFolded ? 'Unfold' : 'Fold' }}" style="margin-right: 1px">
<button t-on-click="() => this.props.toggleFolded(identifier)" class="o_mrp_bom_unfoldable btn btn-light p-0" t-attf-aria-label="{{ props.isFolded ? 'Unfold' : 'Fold' }}" t-attf-title="{{ props.isFolded ? 'Unfold' : 'Fold' }}" style="margin-right: 1px">
<i t-attf-class="fa fa-fw fa-caret-{{ props.isFolded ? 'right' : 'down' }}" role="img"/>
</button>
</t>
@@ -11,14 +11,6 @@ export class BomOverviewSpecialLine extends Component {
this.formatMonetary = (val) => formatMonetary(val, { currencyId: this.data.currency_id });
}
//---- Handlers ----
onToggleFolded() {
if (this.props.parentId) {
this.props.bus.trigger(`toggle-fold-${this.props.parentId}`);
}
}
//---- Getters ----
get data() {
@@ -52,9 +44,7 @@ export class BomOverviewSpecialLine extends Component {
BomOverviewSpecialLine.template = "mrp.BomOverviewSpecialLine";
BomOverviewSpecialLine.props = {
bus: Object,
type: String,
parentId: { type: String, optional: true },
isFolded: { type: Boolean, optional: true },
showOptions: {
type: Object,
@@ -4,7 +4,7 @@
<tr t-name="mrp.BomOverviewSpecialLine" owl="1">
<td name="td_mrp_bom">
<span t-attf-style="margin-left: {{ data.level * 20 }}px"/>
<button t-if="hasFoldButton" t-on-click="onToggleFolded" t-attf-class="o_mrp_bom_{{ props.isFolded ? 'unfoldable' : 'foldable' }} btn btn-light ps-0 py-0" t-attf-aria-label="{{ props.isFolded ? 'Unfold' : 'Fold' }}" t-attf-title="{{ props.isFolded ? 'Unfold' : 'Fold' }}">
<button t-if="hasFoldButton" t-on-click="props.toggleFolded" t-attf-class="o_mrp_bom_{{ props.isFolded ? 'unfoldable' : 'foldable' }} btn btn-light ps-0 py-0" t-attf-aria-label="{{ props.isFolded ? 'Unfold' : 'Fold' }}" t-attf-title="{{ props.isFolded ? 'Unfold' : 'Fold' }}">
<i t-attf-class="fa fa-fw fa-caret-{{ props.isFolded ? 'right' : 'down' }}" role="img"/>
<t t-if="props.type == 'operations'">Operations</t>
<t t-elif="props.type == 'byproducts'">By-Products</t>
@@ -66,7 +66,6 @@ BomOverviewTable.components = {
BomOverviewComponentsBlock,
};
BomOverviewTable.props = {
bus: Object,
showOptions: {
type: Object,
shape: {
@@ -81,4 +80,5 @@ BomOverviewTable.props = {
uomName: { type: String, optional: true },
currentWarehouseId: { type: Number, optional: true },
data: Object,
changeFolded: Function,
};
@@ -40,16 +40,15 @@
</thead>
<tbody>
<BomOverviewLine
bus="props.bus"
showOptions="props.showOptions"
currentWarehouseId="props.currentWarehouseId"
data="data"/>
<BomOverviewComponentsBlock
bus="props.bus"
showOptions="props.showOptions"
currentWarehouseId="props.currentWarehouseId"
data="data"/>
data="data"
changeFolded.bind="props.changeFolded"/>
</tbody>
<tfoot t-if="showCosts">
<tr>
@@ -5,7 +5,6 @@
<xpath expr="//t[@name='byproducts']" position="after">
<t t-if="data.subcontracting">
<BomOverviewSpecialLine
bus="props.bus"
type="'subcontracting'"
showOptions="props.showOptions"
data="props.data"/>