Manage CSS Assets By Page (Odoo) - odoo

What is the best way to incorporate css / js assets into Odoo's website where the assets are only loaded for a particular page?
In the examples and documentation they speak of dumping your assets into Odoo's website.assets_frontend and I do this however there are circumstances where I would like to use website templates found online and I really do not want to take the time to look through the css classes and identify conflicts.
If the page itself were to fail that is one thing but if it breaks all the css on my existing pages that is another.
I was thinking of using a technique like this.
t-if="request.httprequest.path.startswith('/page/path/')"
Using an if statement to determine whether or not to incorporate the css in the website assets or not.
<odoo>
<data>
<template id="page_style" name="Page Style" inherit_id="website.assets_frontend">
<xpath expr="link[last()]" position="after">
<t t-if="request.httprequest.path.startswith('/page/path/')">
<link href="/addon_name/path/to/css/style.css" rel="stylesheet" type="text/css"/>
</t>
</xpath>
</template>
</data>
</odoo>
Anyways, if anyone would like to make a suggestion on how they incorporate css into Odoo's frontend assets in a contained way I would appreciate it.

What you can do is actually insert a:
<head>
<link href="/addon_name/path/to/css/style.css" rel="stylesheet" type="text/css"/>
</head>
to your template that you want the specific css/js to be applied to. For a specific example see addons/website_google_map/views/google_map_templates.xml
Your the contents of your head tag will be inserted inside the head tag of the final HTML that will be rendered for that template.
Since it seems to be straighforward and used by the framework itself I have resorted on using it on my own with no problems so far. As I can understand you can also create a javascript Widget that will operate on your template only that will apply a specific css. But the above solution seems cleaner to me.

Related

custom layout in form views in Odoo 14

I need a form view and I need its layout to be customized, using directly the Bootstrap 4 styles
How exactly can I do that ?
Also
I need some fields/tabs to appear conditionally (if some values is true) and such conditionally appearing fields need to be in my custom layout
Is this possible ?
How ?
First of all, I could use an example of a custom layout
And then I could use some enlightenment on how the conditional appearing of fields is done, behind the scenes
Thanks in advance
You can create a form view using any html you like. You can also use xpath to load custom css and javascript, such as bootstrap. You should load the xpath straight after your opening form tag.
<xpath expr="." position="inside">
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.4.1/css/bootstrap.min.css" integrity="sha384-Vkoo8x4CGsO3+Hhxv8T/Q5PaXtkKtu6ug5TOeNV6gBiFeWPGFN9MuhOf23Q9Ifjh" crossorigin="anonymous">
</xpath>
There a couple of ways to show things conditionally. I find the following example easiest when using the form views:
<div id="my-div" attrs="{'invisible': [('field','==',True)]}">Do not show this text if the field is true</div>

How can i upload html5 bootstrap theme to odoo?

I have odooo online account, how can i import bootstrap theme purchased on themeforest, in the odoo? or what i should do to convert current normal theme to be working with odoo?
you could try to add the css file and the js-script file to your assets_common. Odoo will then minimise all the CSS and JS Files into one (or slightly more) files.
In addons/web/views/webclient_templates.xml you can see how the built in bootstrap is added in odoo.
So if you want to add something to all of the javascript files you can do it like this:
<template id="assets_frontend" inherit_id="web.assets_frontend" name="<name of your addition>" priority="15">
<xpath expr="//script[last()]" position="after">
<script type="text/javascript" src="<path to your js file>"</script>
</xpath>
But adding a CSS or JS that isn't built for odoo might cause problems since selectors might be overwritten or you use different bootstrap versions.
I havent't tried it with Bootstrap Themes myself so there might be better solutions.

How to handle paths of JS and CSS in Golang Templates

currently am working in a Golang Site, as frontend I am using the go templates. In order to separate the different parts of the sites I created this templates:
Head: containing the <head> tag, and some imports of css
Header: defining the navbar of the site, logo, etc. It's only HTML
Footer: defining the HTML of the footer of the site.
SomePage: defining the body tag, this template calls Head, Header and footer. This file can be for example the index, the login, etc.
I added the Javascript imports just after I nest the footer template, but still inside the body tag. As example, I added them like:
<script src="public/js/SomeJS.js"></script>
<link href="public/css/SomeCSS.css" type="text/css" rel="stylesheet"/>
In the routes of my project I have defined public to serve those static files, this is working pretty nice. Now, I have some routes of the project, lets say:
router.GET("/",controllers.Index)
router.GET("/login",controllers.Login)
With the first route, the libraries are being loaded pretty well. Then, with routes as the second, I am not able to load them because the browser tries to locate that files as:
http://myserver/login/public/css/someCSS.css instead of
http://myserver/public/css/someCSS.css
In this case, I understand why it's adding the login to the URL. So, my question is, how it's normally handled?
By now I added the domain and folder to the imports, example:
<script src="MyDomain.com/public/js/SomeJS.js"></script>
But I really don't want to do it in this way, because anytime that the domain change I should be editing the code and it's not really pratical. Also, I don't want to add the imports of the libraries in every view that I create. I have some files (CSS and JS) that are common for all the project and I just want writte it once.
Thank you!
Add / in the being of the path, it is called relative path from domain root.
<script src="/public/js/SomeJS.js"></script>
<link href="/public/css/SomeCSS.css" type="text/css" rel="stylesheet"/>
Without /, it is called as relative path from current domain directory. This is the behavior you have right now.
Output:
http://myserver/public/css/someCSS.css
http://myserver/public/js/SomeJS.js

Vue.js - Friendly syntax without compilation templates

Vue.js is ideal library for my case, but I use it on non-SPA page.
Is there a way to bypass syntax v-bind:click? I would like the attributes starts from data-v-* and don't contains :.
My solution (based on accepted answer):
It looks like Vue.js will not pass the exam here.
Knockout proved to be the ideal library for friendly SEO html syntax without compilation templates.
You can use script templates to "hide" your Vue-HTML from the validator. The following validates as HTML5.
<!DOCTYPE html>
<html>
<head>
<title>Whatever</title>
</head>
<body>
<script id="some-template" type="text/template">
<div v-model="foo" v-bind:click="dontCare">Whatever</div>
</script>
<some-template id="app"></some-template>
</body>
</html>
This is not as much of a cheat as it might seem, since Vue-HTML is not HTML, but is in fact a template used for generating HTML (or, I think more accurately, for generating the DOM). But it is a complete cheat in the sense that the generated HTML is never subjected to the validator. :)
Alternatively, you could look at using Knockout, which uses pure HTML5 (what you write is what is delivered to the browser). It is not as performant as Vue, but it is an MVVM framework.
Short answer is: No.
I don't think there is a way to change the templating of Vue. The generated HTML shipped to user will be valid, because modifiers (v-for, v-bind, etc.) will be stripped of your HTML. Framework like Angular, for example, does not strip the multiple "ng-*" properties. For instance, you could write:
<div v-if="model.length" />
The resulting html will be:
<div />
Which is valid and compatible with any W3C validator.

Referring to redirect URL in Velocity template

So I'm trying to render a page's URL in the head of the document, for use with rel=canonical. This is on a site running off Velocity templates. The type of content I'm talking about is specifically a quiz -- which has multiple pages, one for each question, not to mention different URL paramters reflecting how many answers the user has gotten correct.
The site has redirect rules in place to generate the URL for the quiz. They look like this:
<rule>
<from>^/([a-zA-Z_0-9\-]*)/(quiz_[a-zA-Z_0-9\-]*)/(\d*).htm$</from>
<to>/contentdata/quiz.htm?path=/$1/$2.xml&qnum=$3</to>
</rule>
All this is by way of explaining that I'm using this Velocity code:
<link rel="canonical" href="$link.self" />
On the template for this page:
http://example.com/fun/quiz_best_quiz_ever/1.htm
Which produces this HTML:
<link rel="canonical" href="/contentdata/quiz.htm" />
But what I want is this HTML:
<link rel="canonical" href="http://example.com/fun/quiz_best_quiz_ever/" />
Is that clear enough? I know this is complicated, but does anyone have any idea as to how I may be able to accomplish it?
Your Velocity template needs to know what the rest of the URL is. You didn't explain how you are rendering the Velocity. Is it Spring? Velocity Servlet? Some other system?
The basic idea is that you need another reference called $baseUrl. Set this in your java code before the Velocity template is merged
(in Java)
context.put("baseUrl", "http://example.com/fun/quiz_best_quiz_ever");
(in Velocity)
<link rel="canonical" href="$baseUrl/$link.self" />