I have been trying to add pages to my SplitApp from other views (view.js) with their own drivers, but doing so causes the following error:
Sap-ui-core.js: 174 Uncaught Error: failed to load 'view / GestionDePlanta.view.js' from openui5-1.40.8 / resources / view / GestionDePlanta.view.js: 404 - Not Found (...)
I think it has to do with the paths to access that view the moment it boots
Sap.ui.view ({id: "GestionDePlanta", viewName: "view.GestionDePlanta", type: sap.ui.core.mvc.ViewType.JS});
Anyone know any way to do it?
I was following a tutorial, which I found easy to understand, but apparently this is incomplete :
http://blog.mypro.de/2014/02/14/add-page-to-ui5-boilerplate/
Thank you so much.
Index.html
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta charset="UTF-8">
<title>DatosMaestros</title>
<script id="sap-ui-bootstrap"
src="/openui5-1.40.8/resources/sap-ui-core.js"
data-sap-ui-libs="sap.m,sap.ui.commons,sap.ui.table"
data-sap-ui-theme="sap_bluecrystal"
data-sap-ui-compatVersion="edge"
</script>
<link rel="stylesheet" type="text/css" href="css/style.css">
<script type="text/javascript" src="js/utilityFunction.js"></script>
<script type="text/javascript" src="js/xml2json.js"></script>
<script>
sap.ui.localResources("P_GestionDePlanta");
var url = "http://services.odata.org/V4/Northwind/Northwind.svc/Employees",
oModel = new sap.ui.model.json.JSONModel(url, true);
sap.ui.getCore().setModel(oModel);
var app = new sap.m.SplitApp("appId",{mode:sap.m.SplitAppMode.ShowHideMode});
var master = sap.ui.view({id:"GestionDePlanta", viewName:"view.GestionDePlanta", type:sap.ui.core.mvc.ViewType.JS});
app.addMasterPage(master);
var detail = sap.ui.view({id:"PlanAbastecimiento", viewName:"view.PlanAbastecimiento", type:sap.ui.core.mvc.ViewType.JS});
app.addDetailPage(detail);
app.placeAt("content");
</script>
</head>
<body class="sapUiBody" id="content">
</body>
</html>
Component.js
sap.ui.define([
"sap/ui/core/UIComponent",
"sap/ui/Device",
"P_GestionDePlanta/model/models"
], function(UIComponent, Device, models) {
"use strict";
return UIComponent.extend("P_GestionDePlanta.Component", {
metadata: {
manifest: "json"
},
/**
* The component is initialized by UI5 automatically during the startup of the app and calls the init method once.
* #public
* #override
*/
init: function() {
// call the base component's init function
UIComponent.prototype.init.apply(this, arguments);
// set the device model
this.setModel(models.createDeviceModel(), "device");
}
});
});
Manifiest.json
{
"_version": "1.1.0",
"sap.app": {
"_version": "1.1.0",
"id": "P_GestionDePlanta",
"type": "application",
"i18n": "i18n/i18n.properties",
"applicationVersion": {
"version": "1.0.0"
},
"title": "{{appTitle}}",
"description": "{{appDescription}}",
"sourceTemplate": {
"id": "ui5template.basicSAPUI5ApplicationProject",
"version": "1.32.0"
}
},
"sap.ui": {
"_version": "1.1.0",
"technology": "UI5",
"icons": {
"icon": "",
"favIcon": "",
"phone": "",
"phone#2": "",
"tablet": "",
"tablet#2": ""
},
"deviceTypes": {
"desktop": true,
"tablet": true,
"phone": true
},
"supportedThemes": [
"sap_hcb",
"sap_bluecrystal"
]
},
"sap.ui5": {
"_version": "1.1.0",
"rootView": {
"viewName": "P_GestionDePlanta.view.GestionDePlanta",
"type": "JS"
},
"dependencies": {
"minUI5Version": "1.30.0",
"libs": {
"sap.ui.core": {},
"sap.m": {},
"sap.ui.layout": {}
}
},
"contentDensities": {
"compact": true,
"cozy": true
},
"models": {
"i18n": {
"type": "sap.ui.model.resource.ResourceModel",
"settings": {
"bundleName": "P_ProcesamientoDeArchivos.i18n.i18n"
}
}
},
"resources": {
"css": [{
"uri": "css/style.css"
}]
}
}
}
Folders
Image:
Well that tutorial you followed is quite outdated. You would want to use a Component based structure (You have a component in your sample but never use it). The official SAPUI5/OpenUI5 Developer Guide especially the walkthroughs are mostly up to date. I recommend you to do the walkthrough there.
Back to your problem: UI5 has its own way to resolve modules (≈javascript files) from names.
In your example you give UI5 the name of a view: "view.GestionDePlanta". view is the namespace and GestionDePlanta is the module name. So UI5 looks for the namespace view and – lacking any matching namespace-path-mappings – it defaults to the UI5 framework itself using the same path as the sap-ui-core.js you defined in the bootstrap <script> element: ./openui5-1.40.8/resources/view.
To add such an namespace-path-mapping you can use the sap.ui.localResources() function.
With your sap.ui.localResources("P_GestionDePlanta"); declaration UI5 would look for a module "P_GestionDePlanta.view.GestionDePlanta" in the folder ./P_GestionDePlanta/view.
Thats better already but your folder structure should look like this then:
+ P_GestionDePlanta
+ view
GestionDePlanta.view.js
+ controller
GestionDePlanta.controller.js
index.html
An other way would be to use jQuery.sap.registerModulePath() to add an namespace-path-mapping. With jQuery.sap.registerModulePath("P_GestionDePlanta", "./"); UI5 would look for a module "P_GestionDePlanta.view.GestionDePlanta" in the folder ./view.
With that you can keep your folder structure:
+ view
GestionDePlanta.view.js
+ controller
GestionDePlanta.controller.js
index.html
But either way you have to supply the full namespace starting with P_GestionDePlanta everywhere like so:
sap.ui.view({id:"GestionDePlanta", viewName:"P_GestionDePlanta.view.GestionDePlanta", type:sap.ui.core.mvc.ViewType.JS});
Related
I'm using Snowpack + Svelte. After upgrading to Snowpack 3 is not working anymore and I can't configure mount in snowpack.config.js properly.
Don't understand exactly why it cannot find App.js also it's trying to find .jsx, .ts...
[404] /_dist_/screens/App.js
index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<link rel="stylesheet" href="global.css">
<script type="module" defer src="_dist_/main.js"></script>
</head>
<body>
</body>
</html>
And then in my snowpack.config.js
/** #type {import("snowpack").SnowpackUserConfig } */
module.exports = {
mount: {
public: '/',
src: '/_dist_',
},
plugins: [
'#snowpack/plugin-svelte',
'#snowpack/plugin-dotenv',
],
routes: [
/* Enable an SPA Fallback in development: */
// {"match": "routes", "src": ".*", "dest": "/index.html"},
],
optimize: {
/* Example: Bundle your final build: */
// "bundle": true,
},
packageOptions: {
/* ... */
},
devOptions: {
/* ... */
},
buildOptions: {
/* ... */
},
alias: {
components: './src/components',
screens: './src/screens',
lib: './src/lib'
},
};
I also tried:
mount: {
// Same behavior as the "src" example above:
"src": {url: "/dist"},
// Mount "public" to the root URL path ("/*") and serve files with zero transformations:
"public": {url: "/", static: true, resolve: false}
},
So now it's complaining less but still not working
[snowpack] [404] /_dist_/main.js
Files structure
root
--node-modules
--public
----global.css
----index.html
--src
----components
----lib
----screens
----main.js
--snowpack.config.js
...
package.json
"devDependencies": {
"#snowpack/plugin-dotenv": "^2.0.5",
"#snowpack/plugin-svelte": "^3.5.0",
"#snowpack/web-test-runner-plugin": "^0.2.1",
"#testing-library/svelte": "^3.0.3",
"#web/test-runner": "^0.12.2",
"chai": "^4.2.0",
"smart-webcomponents": "^9.0.0",
"snowpack": "^3.0.10",
"svelte": "^3.31.2",
"svelte-i18n": "^3.3.0"
}
Any help or idea will be really appreciated.
Just add .svelte when you import your components.
import App from 'screens/App.svelte'
Please, check this https://github.com/snowpackjs/snowpack/pull/2014#issuecomment-756624333 if you wanna dive deeper.
As it is said in the 20 lesson of the walkthroug, i'm trying to instanate a model with Invoices.json. But as a result i receive "No data" in a List. I've compared all my sources with the onces they have in a tutorial, and they are the same (excluding urls in the index.html)
As far as I understand, the version of the SDK I use is "1.48.10" (i check it in a sap-ui-version.json), so the instanation should work.
Here is my index.html:
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta charset="utf-8">
<title>Walkthrough</title>
<script src="http://localhost:63342/TestOprnUI5/resources/sap-ui-core.js"
id="sap-ui-bootstrap"
data-sap-ui-theme="sap_bluecrystal"
data-sap-ui-libs="sap.m"
data-sap-ui-compatVersion="edge"
data-sap-ui-preload="async"
data-sap-ui-resourceroots='{
"sap.ui.demo.wt": "./testoprnui5/"
}'>
</script>
<script>
sap.ui.getCore().attachInit(function () {
new sap.m.Shell({
app: new sap.ui.core.ComponentContainer({
name: "sap.ui.demo.wt"
})
}).placeAt("content");
});
</script>
</head>
<body class="sapUiBody" id="content">
</body>
</html>
Here is InvoiceList.view,xml:
<mvc:View
xmlns="sap.m"
xmlns:mvc="sap.ui.core.mvc">
<List
headerText="{i18n>invoiceListTitle}"
class="sapUiResponsiveMargin"
width="auto"
items="{invoice>/Invoices}" >
<items>
<ObjectListItem
title="{invoice>Quantity} x {invoice>ProductName}"/>
</items>
</List>
</mvc:View>
Here is App.view.xml:
<mvc:View
controllerName="sap.ui.demo.wt.controller.App"
xmlns="sap.m"
xmlns:mvc="sap.ui.core.mvc"
displayBlock="true">
<App class="myAppDemoWT">
<pages>
<Page title="{i18n>homePageTitle}">
<headerContent>
<Button
icon="sap-icon://hello-world"
press="onOpenDialog"/>
</headerContent>
<content>
<mvc:XMLView viewName="sap.ui.demo.wt.view.HelloPanel"/>
<mvc:XMLView viewName="sap.ui.demo.wt.view.InvoiceList"/>
</content>
</Page>
</pages>
</App>
</mvc:View>
Here is component.js:
sap.ui.define([
"sap/ui/core/UIComponent",
"sap/ui/model/json/JSONModel",
"sap/ui/demo/wt/controller/HelloDialog"
], function (UIComponent, JSONModel, HelloDialog) {
"use strict";
return UIComponent.extend("sap.ui.demo.wt.Component", {
metadata: {
manifest: "json"
},
init: function () {
// call the init function of the parent
UIComponent.prototype.init.apply(this, arguments);
// set data model
var oData = {
recipient: {
name: "World"
}
};
var oModel = new JSONModel(oData);
this.setModel(oModel);
// set dialog
this._helloDialog = new HelloDialog(this.getRootControl());
},
openHelloDialog: function () {
this._helloDialog.open();
}
});
});
Here is the project structure:
TestOpenUI5
- resources
- testopenui5
-- controller
--- App.controller.js
--- HelloDialog.js
--- HelloPanel.controller.js
-- css
--- styles.css
-- i18n
--- i18n.properties
-- view
--- App.view.xml
--- HelloDialog.fragment.xml
--- HelloPanel.view.xml
--- InvoiceList.view.xml
-- Component.js
-- Invoices.json
-- manifest.json
- index.html
- Invoices.json
PS: i've tried to put Invoices.json to the different folders, to the root and to the /testopenui5 folder with the same result.
PPS: it looks like Invoices are not included to the model, but how can i check it to be sure? And where can i find some logs?
You should set the model in manifest.json file.Inside models section of sap.ui5 section you should add three lines of code.
"invoice": {
"type": "sap.ui.model.json.JSONModel",
"uri": "Invoices.json"
}
Yeap, sorry, i've checked my manifest.json not carefully.
The problem was in i've placed invoice section not inside models, but near it.
That is what i had:
"models": {
"i18n": {
"type": "sap.ui.model.resource.ResourceModel",
"settings": {
"bundleName": "sap.ui.demo.wt.i18n.i18n"
}
}
},
"invoice": {
"type": "sap.ui.model.json.JSONModel",
"uri": "Invoices.json"
},
"resources": {
"css": [
{
"uri": "css/style.css"
}
]
}
That is what it should be:
"models": {
"i18n": {
"type": "sap.ui.model.resource.ResourceModel",
"settings": {
"bundleName": "sap.ui.demo.wt.i18n.i18n"
}
},
"invoice": {
"type": "sap.ui.model.json.JSONModel",
"uri": "Invoices.json"
}
},
"resources": {
"css": [
{
"uri": "css/style.css"
}
]
}
We wrote a custom library that we now want to reference in our main application.
Thus we added the following two entries to the consumer's neo-app.json:
{
"path": "/webapp/resources/some/lib",
"target": {
"type": "application",
"name": "somedemolib"
},
"description": "..."
}, {
"path": "/resources/some/lib",
"target": {
"type": "application",
"name": "somedemolib"
},
"description": "..."
}
and the following to the manifest.json of the libs consumer:
"dependencies": {
"minUI5Version": "1.30.0",
"libs": {
...
"some.lib": {
"minVersion": "1.0.0"
}
}
},
However upon loading the web-app I can see a HTTP404 when trying to load the library under the following path:
Uncaught Error: failed to load 'some/lib/library.js' from ../../resources/some/lib/library.js: 404 - Not Found
You have to declare your custom scripts in the first lines of your components.js
First of all you have to declare the path of your custom lib folder:
https://sapui5.netweaver.ondemand.com/sdk/docs/api/symbols/jQuery.sap.html#.registerModulePath
jQuery.sap.registerResourcePath("libs/custom", "/scripts/customlibs");
After that call you are able to load your script from that path with this call:
jQuery.sap.require("libs.custom.nameofyourscript");
"libs.custom" points to that folder you have registered previously and then your are able to import the script by its name. So your components.js looks like this:
jQuery.sap.registerResourcePath("libs/custom", "/scripts/customlibs");
jQuery.sap.require("libs.custom.nameofyourscript");
// Now the declaration of the components starts
sap.ui.core.UIComponent.extend("yourappname.Component", {
// ...
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<script src="resources/sap-ui-core.js"
id="sap-ui-bootstrap"
data-sap-ui-libs="sap.m,sap.ui.table,sap.ui.commons"
data-sap-ui-theme="sap_bluecrystal">
</script>
<!-- only load the mobile lib "sap.m" and the "sap_mvi" theme -->
<script>
var bFlag;
sap.ui.localResources("views");
sap.ui.localResources("i18n");
sap.ui.localResources("utils");
jQuery.sap.registerModulePath('Application', 'Application');
jQuery.sap.require("Application");
var oApp = new Application({
root : "content"
});
</script>
<link href="css/stylesheet.css" rel="stylesheet" type="text/css">
</head>
<body class="sapUiBody" role="application">
<div id="content"></div>
</body>
</html>
I am developing a sapui5 application in which I have a split app,now on the detail page in the toolbar I have a button called open in new window.So I want to open this particular detail page(only detail page) in a new tab on clicking this button.
Can anyone help me on this as in how to go about it?
Thanks in advance.
Regards,
Shalini
Use the SAP's Router API.
Basically, define your router, routes, pattern and targets objects in your manifest.json file:
"sap.ui5": {
"rootView": {
"viewName": "path.to.view.name",
"type": "XML",
"async": true
},
"routing": {
"config": {
"routerClass": "sap.m.routing.Router",
"viewType": "XML",
"viewPath": "path.to.view",
"controlId": "init",
"controlAggregation": "pages",
"async": true
},
"routes": {
"init": {
"pattern": "",
"target": "init",
"viewId": "vid_init"
},
"target_name": {
"pattern": "url_parameter",
"target": "target_name",
"viewId": "vid_view_name"
}
},
"targets": {
"target_name": {
"viewName": "view_name",
"transition": "show"
}
}
}
}
Assign a press event handler in your button's properties:
<Button id="myButton" press=".onOpenNewWindow" />
In your view's controller write a code to handle your event. Example:
onOpenNewWindow: funtion(oEvent){
sap.ui.require([
"sap/m/library"
], sapMLib => sapMLib.URLHelper.redirect("#/url_parameter", /*new window*/true));
},
Resources
API Reference: sap.m.URLHelper.redirect
Documentation: Routing and Navigation
Basically, you can open a new tab in JavaScript like this:
window.open("<yourURL>", _blank');
For your SAPUI5 Application you simply have to provide an additional .html file at a dedicated URL which loads your View/Controller. If you want to pass information from the Master/Detail application to the new tab you could add URL parameters.
As I can see in your edited question you´re using an Application. I don´t know the further structure (especially what your Application.js does) but in a separate .html a very simple solution could look like this:
<script>
sap.ui.localResources("views");
sap.ui.localResources("i18n");
sap.ui.localResources("utils");
sap.ui.jsview("name.of.your.detailView").placeAt("content");
</script>
If you want to reuse your Application.js file you can extend it and pass a simple parameter which tells to display only one View.
One more thing: I guess you´re using sap.m.SplitApp somewhere in your application. To display only the DetailView you should use sap.m.App instead at that point.
I am trying to use the new chrome notifications, nothing fancy just trying to a basic one to work, but i keep getting
Uncaught TypeError: Cannot call method 'create' of undefined
I think its the manifest but I'm not sure what I'm doing wrong, anyone have any ideas?
Thanks in advance
Javascript
var id= 0;
var opt={
type:"basic",
title:"Hello",
message:"world",
iconUrl:"Google.png"
}
function creationCallback(id) {
console.log("Succesfully created " + id + " notification");
}
function createnot()
{
chrome.notifications.create(id, opt, creationCallback);
id++;
}
manifest
{
"name": "Notification API Sample",
"description": "Tests the notification API",
"manifest_version" : 2,
"version" : "0.1",
"permissions" : [
"notifications"
]
}
HTML
<html>
<head>
<script type="text/javascript" src="note.js"></script>
<link href="style.css" rel="stylesheet" type="text/css" />
</head>
<body>
<input type="button" value="meh" onclick="createnot()"/>
<footer>
</footer>
</body>
</html>
{
"name": "Notification API Sample",
"description": "Tests the notification API",
"manifest_version" : 2,
"version" : "0.1",
"permissions" : [
"notifications",
"http://*/*" // add this if your html file is a webpage not a page in extension.
],
"background": {
"scripts": ["background.js"],
"persistent": false // add this line if you use event page.
}
}
Your manifest.json needs the information of "background" like this.
Also, if your html page is a webpage not a page in extension itself,
You need to give a permission for it.
var id = "0";
It may not make much difference but,I think notification id needs to be a string.
chrome.notifications.create(string notificationId, NotificationOptions options, function callback)
+++Edited+++
foo.js
$(function(){
var test = $("#test");
test.click(function () {
chrome.notifications.create(
'id1',{
type:"basic",
title:"Hello",
message:"world",
iconUrl:"Google.png"
},
function() {
}
);
});
});
foo.html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<script src="jquery.js"></script>
<script src="options.js"></script>
</head>
<body>
<h1 id="test">This is a test.</h1>
</body>
</html>
manifest.json
{
"name": "Notification API Sample",
"description": "Tests the notification API",
"manifest_version" : 2,
"version" : "0.1",
"permissions" : [
"notifications"
]
}
I think this is the simplest way if the html page is in extension.
You need these files. You don't even need background.js for this.
1.manifest.json
2.foo.html
3.foo.js