sap.ui.define([
"sap/ui/core/mvc/Controller"
], function (Controller) {
"use strict";
return Controller.extend("app.controller.HomePage", {
onInit: function () {},
onTilePress: function () {
this.getOwnerComponent().getRouter().navTo("RouteSecondPage");
}
});
});
sap.ui.define([
"app/controller/Navigation"
], function (Navigation) {
"use strict";
return Navigation.extend("app.controller.SecondPage", {
onInit: function () {},
onTilePress: function () {
this.getOwnerComponent().getRouter().navTo("RouteTabPage");
}
});
});
sap.ui.define([
"sap/ui/core/mvc/Controller",
"sap/ui/core/routing/History"
], function (Controller, History) {
"use strict";
return Controller.extend("app.controller.Navigation", {
onNavBack: function () {
var iIndex = this.getHistoryRouteBackIndex();
if (iIndex > 0) {
window.history.go(iIndex * -1);
} else {
this.onNavHome();
}
},
getHistoryRouteBackIndex: function () {
var oHistory = History.getInstance();
var sRoute = this.getRouteFromHash(location.hash.substring(2)); // User current hash as route reference.
var iHistoryBack = 0;
for (var i = oHistory.iHistoryPosition; i >= 0; i--) { // Start at current history position and go down.
if (sRoute !== this.getRouteFromHash(oHistory.aHistory[i])) { // Route change found. We return the index of route change.
return iHistoryBack;
}
iHistoryBack++; // History still on same route. Count history index up.
}
return iHistoryBack;
},
getRouteFromHash: function (sHash) {
var aHashes = sHash.split("/");
var sRoute;
for (var i = 0; i < aHashes.length; i++) {
if (!aHashes[i].startsWith("-")) {
sRoute = aHashes[i];
break;
}
}
return sRoute;
},
navOneStepBack: function () {
var oHistory = History.getInstance();
var sPreviousHash = oHistory.getPreviousHash();
// The history contains a previous entry
if (sPreviousHash !== undefined) {
window.history.go(-1);
} else {
this.onNavHome(); //if no hash change found navigate to home page
}
},
onNavHome: function () {
this.getOwnerComponent().getRouter().navTo("RouteHomePage");
}
});
});
sap.ui.define([
"app/controller/Navigation"
], function (Navigation) {
"use strict";
return Navigation.extend("app.controller.TabPage", {
onInit: function () {},
//It will record a history if between of tabs a nagivation have been made
handleNavigate: function (oEvent) {
var oSection = oEvent.getParameter("section");
var sKey = oSection && oSection.data("key");
if (sKey) {
this.getOwnerComponent().getRouter().navTo("RouteTabPage", {tab: sKey});
}
}
});
});
<mvc:View controllerName="app.controller.HomePage" xmlns:mvc="sap.ui.core.mvc" displayBlock="true" xmlns="sap.m">
<Shell id="shell">
<App id="app">
<pages>
<Page id="page" title="HomePage">
<content>
<GenericTile class="sapUiTinyMarginBegin sapUiTinyMarginTop tileLayout" header="Click me to go second page" press="onTilePress">
<TileContent>
<ImageContent src="sap-icon://touch"/>
</TileContent>
</GenericTile>
</content>
</Page>
</pages>
</App>
</Shell>
</mvc:View>
<mvc:View xmlns:mvc="sap.ui.core.mvc" xmlns="sap.uxap" xmlns:layout="sap.ui.layout" xmlns:m="sap.m" xmlns:ui="sap.ui.table" xmlns:app="http://schemas.sap.com/sapui5/extension/sap.ui.core.CustomData/1"
xmlns:form="sap.ui.layout.form" controllerName="app.controller.TabPage" height="100%">
<!-- A BAR WITH NAVBACK and NAVHOME BUTTON-->
<m:Bar design="Header">
<m:contentLeft>
<m:Button text="Back" type="Default" icon="sap-icon://nav-back" iconFirst="true" width="auto" class="sapUiLargeMarginEnd" iconDensityAware="false"
press="onNavBack"/>
<m:Button text="Home" type="Emphasized" icon="sap-icon://home" width="auto" class="sapUiNoMargin" iconDensityAware="false"
press="onNavHome"/>
</m:contentLeft>
</m:Bar>
<!-- OBJECTPAGELAYOUT WITH 6 TABs-->
<ObjectPageLayout id="ObjectPageLayout" navigate="handleNavigate" enableLazyLoading="false" useIconTabBar="true"
alwaysShowContentHeader="false" showFooter="false" showTitleInHeaderContent="false">
<headerTitle>
<ObjectPageHeader objectTitle="Navigation between tabs" showMarkers="false" markFlagged="false"/>
</headerTitle>
<sections>
<ObjectPageSection id="tab1" app:key="tab1" title="Tab1">
<subSections>
<ObjectPageSubSection title="Tab1">
<blocks>
<form:SimpleForm title="One"/>
</blocks>
</ObjectPageSubSection>
</subSections>
</ObjectPageSection>
<ObjectPageSection id="tab2" app:key="tab2" title="Tab2">
<subSections>
<ObjectPageSubSection title="Tab2">
<blocks>
<form:SimpleForm title="Two"/>
</blocks>
</ObjectPageSubSection>
</subSections>
</ObjectPageSection>
<ObjectPageSection id="tab3" app:key="tab3" title="Tab3">
<subSections>
<ObjectPageSubSection title="Tab3">
<blocks>
<form:SimpleForm title="Three"/>
</blocks>
</ObjectPageSubSection>
</subSections>
</ObjectPageSection>
<ObjectPageSection id="tab4" app:key="tab4" title="Tab4">
<subSections>
<ObjectPageSubSection title="Tab4">
<blocks>
<form:SimpleForm title="Four"/>
</blocks>
</ObjectPageSubSection>
</subSections>
</ObjectPageSection>
<ObjectPageSection id="tab5" app:key="tab5" title="Tab5">
<subSections>
<ObjectPageSubSection title="Tab5">
<blocks>
<form:SimpleForm title="Five"/>
</blocks>
</ObjectPageSubSection>
</subSections>
</ObjectPageSection>
<ObjectPageSection id="tab6" app:key="tab6" title="Tab6">
<subSections>
<ObjectPageSubSection title="Tab6">
<blocks>
<form:SimpleForm title="Six"/>
</blocks>
</ObjectPageSubSection>
</subSections>
</ObjectPageSection>
</sections>
</ObjectPageLayout>
</mvc:View>
<mvc:View xmlns:core="sap.ui.core" xmlns:mvc="sap.ui.core.mvc" xmlns="sap.m"
controllerName="app.controller.SecondPage" xmlns:html="http://www.w3.org/1999/xhtml">
<Page id="page" title="SecondPage" showNavButton="true" navButtonPress="onNavBack">
<content>
<GenericTile class="sapUiTinyMarginBegin sapUiTinyMarginTop tileLayout" header="Click me to go tabs" press="onTilePress">
<TileContent>
<ImageContent src="sap-icon://legend"/>
</TileContent>
</GenericTile>
</content>
</Page>
</mvc:View>
sap.ui.define([
"sap/ui/core/UIComponent"
], function (UIComponent) {
"use strict";
return UIComponent.extend("app.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);
// enable routing
this.getRouter().initialize();
}
});
});
{
"_version": "1.12.0",
"sap.app": {
"id": "app",
"type": "application",
"i18n": "i18n/i18n.properties",
"applicationVersion": {
"version": "1.0.0"
},
"title": "{{appTitle}}",
"description": "{{appDescription}}",
"sourceTemplate": {
"id": "ui5template.basicSAPUI5ApplicationProject",
"version": "1.40.12"
}
},
"sap.ui": {
"technology": "UI5",
"icons": {
"icon": "",
"favIcon": "",
"phone": "",
"phone@2": "",
"tablet": "",
"tablet@2": ""
},
"deviceTypes": {
"desktop": true,
"tablet": true,
"phone": true
}
},
"sap.ui5": {
"flexEnabled": false,
"rootView": {
"viewName": "app.view.HomePage",
"type": "XML",
"async": true,
"id": "Home"
},
"dependencies": {
"minUI5Version": "1.65.6",
"libs": {
"sap.m": {},
"sap.ui.core": {},
"sap.ui.layout": {}
}
},
"contentDensities": {
"compact": true,
"cozy": true
},
"models": {
},
"resources": {
"css": [
{
"uri": "css/style.css"
}
]
},
"routing": {
"config": {
"routerClass": "sap.m.routing.Router",
"viewType": "XML",
"async": true,
"viewPath": "app.view",
"controlAggregation": "pages",
"controlId": "app",
"clearControlAggregation": false
},
"routes": [
{
"name": "RouteHomePage",
"pattern": "",
"target": [
"TargetHomePage"
]
},
{
"name": "RouteSecondPage",
"pattern": "SecondPage",
"target": [
"TargetSecondPage"
]
},
{
"name": "RouteTabPage",
"pattern": "TabPage/:tab:",
"target": [
"TargetTabPage"
]
}
],
"targets": {
"TargetHomePage": {
"viewType": "XML",
"viewName": "HomePage"
},
"TargetSecondPage": {
"viewType": "XML",
"viewName": "SecondPage"
},
"TargetTabPage": {
"viewType": "XML",
"viewName": "TabPage"
}
}
}
}
}
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>windowHistoryNavigationProblem</title>
<script
src="https://sapui5.hana.ondemand.com/1.84.13/resources/sap-ui-core.js"
data-sap-ui-theme='sap_belize'
data-sap-ui-libs='sap.m'
data-sap-ui-bindingSyntax='complex'
data-sap-ui-resourceroots='{
"app": "./app"
}'
>
</script>
<script type="text/javascript" src="./App.js"></script>
</head>
<body id="content" class="sapUiBody"></body>
</html>
---------------SAMPLE APP GENERAL INFORMATION-----------------
We have tree views and controllers; HomePage , SecondPage, TabPage
> "HomePage" and "SecondPage" have just a simple tile which navigates other view;
from "HomePage" you can click on tile and navigate "SecondPage"
and from "SecondPage" you can click on tile and navigate "TabPage"
> "TabPage" has ObjectPageLayout with 6 Tabs and this ObjectPageLayout control has
navigate="handleNavigate" event listener that registers tab changes to history.
----------------NAVIGATION LOGIC-------------------------------
> All navigation managed by "Navigation.js" which is in "controller" directory.
> This file has a NavBack function that calls another function which held by "iIndex" variable --> var iIndex = this.getHistoryRouteBackIndex()
- "getHistoryRouteBackIndex()" function checks how many time "hash" changed, until the route changes. And returns this number to "iIndex" variable.
> Depends on "iIndex" value, app navigates "-iIndex" times back in to history.
EXAMPLE 1: If you click back Button from "SecondPage" hash will change and also route will change; thats why "iIndex" will be "1" and app will navigate one step back in history to HomePage.
EXAMPLE 2: If you are in "TabPage" and you are moving between of tabs; "handleNavigate" function will register this tab changes to hash.
Then if you click back button, "iIndex" will count how many times the hash has been change, until route changes.
And app will navigate to last route change point in history; to "SecondPage", instead of navigating between of tabs one step back.
----------------PROBLEM DEFINITION---------------------------------------
> Sapui5 Version 1.71.8
- Navigation logic and window.history works without any problem as expected
> Sapui5 Version 1.84
- If you test "EXAMPLE 2" it works in first round, but in the second turn; althought "iIndex" value greater than "0", "window.history.go(iIndex * -1)" does not react/work anymore
and thus back button does not work.
---------------------------------------------------------------------------
window.onload = function () {
sap.ui.getCore().attachInit(function() {
new sap.ui.core.ComponentContainer({
height : "100%",
name : "app"
}).placeAt("content");
});
};