odoo前端的Patch用法
一、Patching code:根据官方功能解释
我们需要自定义 UI 的工作方式。一些受支持的 API 涵盖了许多常见需求。
例如,所有注册表都是很好的扩展点: 字段注册表允许添加/删除专门的字段组件,或者主组件注册表允许添加应该一直显示的组件。
但是,在某些情况下它是不够的。在这些情况下,我们可能需要就地修改对象或类。为此,Odoo 提供了实用功能patch。
覆盖/更新无法控制的其他一些组件/代码段的行为最有用。
二、Patch源码位置 :../web/static/src/core/utils/patch.js
引用方式: import { patch } from 'web.utils';
patch方法的定义:
/** @odoo-module **/ const patchMap = new WeakMap();
/**
* Patch an object
*
* If the intent is to patch a class, don't forget to patch the prototype, unless
* you want to patch static properties/methods.
* 如果目的是修补一个类,不要忘记修补原型,除非你想修补静态属性方法。
*
* @param {Object} obj 添加补丁的对象
* @param {string} patchName 补丁名
* @param {Object} patchValue 补丁值
* @param {{pure?: boolean}} [options] 其他选项
*/
export function patch(obj, patchName, patchValue, options = {}) {
const pure = Boolean(options.pure);
if (!patchMap.has(obj)) {
patchMap.set(obj, {
original: {},
patches: [],
});
}
const objDesc = patchMap.get(obj);
if (objDesc.patches.some((p) => p.name === patchName)) {
throw new Error(`Class ${obj.name} already has a patch ${patchName}`);
}
objDesc.patches.push({
name: patchName,
patch: patchValue,
pure,
}); for (const k in patchValue) {
let prevDesc = null;
let proto = obj;
do {
prevDesc = Object.getOwnPropertyDescriptor(proto, k);
proto = Object.getPrototypeOf(proto);
} while (!prevDesc && proto); const newDesc = Object.getOwnPropertyDescriptor(patchValue, k);
if (!objDesc.original.hasOwnProperty(k)) {
objDesc.original[k] = Object.getOwnPropertyDescriptor(obj, k);
} if (prevDesc) {
const patchedFnName = `${k} (patch ${patchName})`; if (prevDesc.value && typeof newDesc.value === "function") {
makeIntermediateFunction("value", prevDesc, newDesc, patchedFnName);
}
if ((newDesc.get || newDesc.set) && (prevDesc.get || prevDesc.set)) {
// get and set are defined together. If they are both defined
// in the previous descriptor but only one in the new descriptor
// then the other will be undefined so we need to apply the
// previous descriptor in the new one.
// get和set一起定义。如果它们都在前一个描述符中定义,
// 但在新的描述符中只有一个,那么另一个将是未定义的,因此我们需要在新的描述符中应用前一个描述符。
// 发挥中间作用
newDesc.get = newDesc.get || prevDesc.get;
newDesc.set = newDesc.set || prevDesc.set;
if (prevDesc.get && typeof newDesc.get === "function") {
makeIntermediateFunction("get", prevDesc, newDesc, patchedFnName);
}
if (prevDesc.set && typeof newDesc.set === "function") {
makeIntermediateFunction("set", prevDesc, newDesc, patchedFnName);
}
}
} Object.defineProperty(obj, k, newDesc);
} function makeIntermediateFunction(key, prevDesc, newDesc, patchedFnName) {
const _superFn = prevDesc[key];
const patchFn = newDesc[key];
if (pure) {
newDesc[key] = patchFn;
} else {
newDesc[key] = {
[patchedFnName](...args) {
let prevSuper;
if (this) {
prevSuper = this._super;
Object.defineProperty(this, "_super", {
value: _superFn.bind(this),
configurable: true,
writable: true,
});
}
const result = patchFn.call(this, ...args);
if (this) {
Object.defineProperty(this, "_super", {
value: prevSuper,
configurable: true,
writable: true,
});
}
return result;
},
}[patchedFnName];
}
}
}
案例:设置主题的背景、前景、和图片方法,js部分代码截图

/** @odoo-module */
import { NavBar } from "@web/webclient/navbar/navbar";
import { registry } from "@web/core/registry";
const { fuzzyLookup } = require('@web/core/utils/search');
import { computeAppsAndMenuItems } from "@web/webclient/menus/menu_helpers";
import core from 'web.core';
const commandProviderRegistry = registry.category("command_provider");
import { patch } from 'web.utils';
var rpc = require('web.rpc');
//'backend_theme/static/src/components/app_menu/search_apps.js'
// 字符串名称:官方写法是该js的路径来命名
//对象名称 NavBar.prototype
patch(NavBar.prototype, 'backend_theme/static/src/components/app_menu/search_apps.js', {
//--------------------------------------------------------------------------
// Public 设置背景、前景、悬浮颜色
//--------------------------------------------------------------------------
/**
* @override
*/
setup() {
this._super();
this._search_def = $.Deferred();
let { apps, menuItems } = computeAppsAndMenuItems(this.menuService.getMenuAsTree("root"));
this._apps = apps;
this._searchableMenus = menuItems;
this.colors = this.fetch_data();
},
fetch_data: function() {
var self = this;
rpc.query({model: 'res.config.settings',method: 'config_color_settings',args: [0],}).then(function(result){
self.colors = result;
console.log("$$$",result);
if (result.primary_accent !== false){
document.documentElement.style.setProperty("--primary-accent",result.primary_accent);
}
if (result.appbar_color !== false){
document.documentElement.style.setProperty("--app-bar-accent",result.appbar_color);}
if (result.primary_hover !== false){
document.documentElement.style.setProperty("--primary-hover",result.primary_hover);}
if (result.secondary_color !== false){
document.documentElement.style.setProperty("--primary-accent-border",result.secondary_color);}
if (result.full_bg_img !== false){
document.documentElement.style.setProperty("--full-screen-bg",'url(data:image/png;base64,'+result.full_bg_img+')');
}
if (result.appbar_text !== false){
document.documentElement.style.setProperty("--app-menu-font-color",result.appbar_text);}
if (result.secoundary_hover !== false){
document.documentElement.style.setProperty("--secoundary-hover",result.secoundary_hover);}
if (result.kanban_bg_color !== false){
document.documentElement.style.setProperty("--kanban-bg-color",result.kanban_bg_color);}
});
},
});

odoo前端的Patch用法的更多相关文章
- odoo前端
bootstrap: http://www.runoob.com/bootstrap/bootstrap-tutorial.html javascript: http://www.runoob.com ...
- 十分钟掌握diff&patch用法
作为程序员,了解diff&patch命令是非常必要的.比如说我们发现某个项目有bug代码,而自己又没有svn的提交权限,那么此时最合适的解决方法就是用diff命令做一个补丁发给项目成员.项目成 ...
- Odoo前端页面模版渲染引擎——Jinja2用法教程
转载请注明原文地址:https://www.cnblogs.com/cnodoo/p/9307200.html 一:渲染模版 要渲染一个qweb模板文件,通过render_template方法即可. ...
- svn patch用法
最近遇到了一个patch的使用场景: 有一个同事对源码做了一些修改,但是又不想将源码提交到SVN服务器,而我又想得到他所做的修改. patch的使用方法: 创建patch 在要导出“修改”的目录中,单 ...
- odoo 前端页面渲染--数据库管理页面
例子 - 去除登陆页面的Powered by Odoo链接从上面的第3步,我们可以看到,最后登录界面是由'web.login' 模板来显示的,通过odoo的继承方式,我们很容易的就可以去除这个链接,通 ...
- patch 用法
diff -Nrua a b > c.patch 实例说明: --- old/modules/pcitable Mon Sep 27 11:03:56 1999 +++ new/modules/ ...
- patch用法 (转载)
转载:http://shenze60.blog.163.com/blog/static/315747722009724113026896/ 首先介绍一下diff和patch.在这里不会把man在线文档 ...
- odoo里的rpc用法
import odoorpcdb_name = 'test-12'user_name = 'admin'password = 'admin'# Prepare the connection to th ...
- odoo前端必填提示
- odoo开发笔记 -- related用法
related:字面意思-关联字段,表示本字段引用关联表中的某字段. 格式为:fields.related(关系字段,引用字段,type,relation,string,...),关系字段是本对象的某 ...
随机推荐
- 全程使用 AI 从 0 到 1 写了个小工具
背景 好长时间没写技术方面的文章了,主要的原因是AI的发展实在太快太快,尤其是从去年ChatGPT的普及到今年DeepSeek的爆火,AI的世界可谓是三天一个小变化五天一个大版本,AI的能力每天都在以 ...
- [解决方案][docker] Http: server gave HTTP response to HTTPS client
前言 用centos运行docker不支持http,需要在daemon.json 里面配置一下 目录 没有daemon.json 需要添加这个文件 在daemon.json 增添配置 重启即可 一.l ...
- . net core 项目创建和发布
1.发布和部署到IIS https://www.cnblogs.com/loverwangshan/p/11284169.html https://www.cnblogs.com/wangjiegua ...
- halo配置踩坑过程小记
写在最前: 终于搞定了最后的一步域名解析配置,其实动态博客的折腾程度也不低于当时的hexo吧,也可能当时的痛苦过程已经忘了..整理一下思路,记录一下配置过程走过的坑. 我是从hexo用了半年想 ...
- (C++实现)2-NAF
(C++实现)2-NAF 前言 任何一个非负整数,都有一个唯一的 NAF (Non-adjacent form) 表示. 因着课程的缘由,我不得不研究一下 NAF 是怎么实现的,也是现学现用. ...
- linux php重启
1.停止命令 你可以先查看自己的php进程有没有启动 ps -ef | grep php [root@iZ6we4yxap93y2r0clg3g8Z ~]# ps -ef | grep php roo ...
- “决策-寻找过程”的黄金秘密工具,1/e 法则之应用(尤其日常生活中的应用)
https://www.ccgxk.com/magicword/327.html 目录 引言 著名的 1/e 法则内容和解释 应用到生活中的 1/e 法则是什么样? 相亲案例 看书.看电影案例 生活质 ...
- [每日算法 - 华为机试] leetcode680. 验证回文串 II
入口 力扣https://leetcode.cn/problems/valid-palindrome-ii/submissions/ 题目描述 给你一个字符串 s,最多 可以从中删除一个字符. 请你判 ...
- [COCI2014-2015#2] MOBITEL 题解
题目大意 有一只蚂蚱,它把手机掉到了水坑里.然后它把手机捞出来,发现手机键盘都坏了. 那么手机没有坏之前就是介个样子的: 我们想打字的话就需要按下相应的数字键.比如说我们想打出 "a&quo ...
- mongo db集群故障选举分析
转载请注明出处: 一.MongoDB集群基础架构 1. 副本集(Replica Set)核心原理 节点角色: Primary:唯一可写节点,处理所有写操作和默认读请求 Secondary:异步复制Pr ...