Skip to Content

SAP Fiori Overview Pages introduced a new concept to the user interaction, all the detailed information that the user needs in a single page with the ability to filter and navigate to different applications, and the most important, information displayed in the way that the user wants.

In the current version of SAPUI5 (SAP Innovation 1.46), if we want to create a new card through the WebIDE wizard, these options are available:

  • List
  • Link List
  • Table
  • Stack
  • Analytic Card

But what if we want to implement our own custom card? For example, include a map, an integration with a 3rd party component or even a different UI5 control, is it possible to achieve that?

The answer is Yes! Based on the concept of extension is possible to create your own card from a generic card provided by SAP. To understand the concepts behind the Overview pages and Cards I’m going to split this article in 3 different sections:

  1. Creating a new List card
  2. Debugging the OVP to understand the Generic card concept
  3. Creating a new Custom card

If you already have experience with Overview Pages & Cards you can jump directly to the section 2, if you never had any contact with this Fiori Element I advise you to read all the article.

Let’s start our exercise creating a new List card. In this example I will use the Northwind OData Service to connect the data with our application.

 

Create a new List card

1. Create a new project from template and select the Overview Page Application.

2. Set the name as ZOVPCUSTOMCARD.

 

3. Select the Northwind Odata Services, if you have any questions about how to configure the destination, you can look for further information in this link: https://blogs.sap.com/2014/07/07/how-to-use-northwind-odata-service-with-sap-river-rde/

  • URL: /V2/northwind/northwind.svc

 

4. Leave the annotation selection in blank for now, we’ll generate the annotation in a different step. In the end, provide the information about the Template Customization and click Finish.

 

5. This should be your project structure:

 

6. Right click in the project folder, select New -> Card.

 

7. Define northwind as the Datasource.

 

8. Select the List card option.

 

9. Fill the information in the General section and leave the sections Annotations and Card Properties in blank (no need for this exercise).

 

10. Notice that the project structure continues the same, but if we open the manifest.json it’s possible to check a new section in the end of the file called “sap.ovp”, this is the code generated automatically by the WebIDE wizard:

	"sap.ovp": {
		"globalFilterModel": "northwind",
		"globalFilterEntityType": "Customer",
		"cards": {
			"zovpcustomcard_card00": {
				"model": "northwind",
				"template": "sap.ovp.cards.list",
				"settings": {
					"title": "{{zovpcustomcard_card00_title}}",
					"subTitle": "{{zovpcustomcard_card00_subTitle}}",
					"entitySet": "Customers",
					"addODataSelect": "false",
					"annotationPath": "com.sap.vocabularies.UI.v1.LineItem"
				}
			}
		}
	}

Attention: We need to adjust manually the name of the globalFilterEntityType, the wizard uses the EntitySet instead the EntityType, so just remember to change the name from Customers to Customer (without the S in the end).

 

11. The last step is to create an Annotation file and set the values for the Global Filter and the List.

To achieve that click with the right button in the localService folder and select New -> Annotation File.

 

12. Create a new annotation file with the name annotation_list, this should be your project structure after you finish:

 

13. Edit the annotation_list.xml, first of all we need to annotate the Customers entity set. To define the fields available in the Global filter we need to populate the UI.SelectionFields annotation and for the fields in the list we need to populate the UI.LineItem annotation. Check the example in the XML file below, the fields CustomerID and CompanyName were configured in the filter and in the list.

<edmx:Edmx xmlns:edmx="http://docs.oasis-open.org/odata/ns/edmx" Version="4.0">
	<edmx:Reference xmlns:edmx="http://docs.oasis-open.org/odata/ns/edmx"
		Uri="https://webide-p998901trial.dispatcher.hanatrial.ondemand.com/destinations/northwind/V2/northwind/northwind.svc/$metadata">
		<edmx:Include xmlns:edmx="http://docs.oasis-open.org/odata/ns/edmx" Namespace="NorthwindModel"/>
		<edmx:Include xmlns:edmx="http://docs.oasis-open.org/odata/ns/edmx" Namespace="ODataWeb.Northwind.Model"/>
	</edmx:Reference>
	<edmx:Reference Uri="http://docs.oasis-open.org/odata/odata-data-aggregation-ext/v4.0/cs02/vocabularies/Org.OData.Aggregation.V1.xml">
		<edmx:Include Alias="Aggregation" Namespace="Org.OData.Aggregation.V1"/>
	</edmx:Reference>
	<edmx:Reference Uri="http://docs.oasis-open.org/odata/odata/v4.0/errata03/os/complete/vocabularies/Org.OData.Capabilities.V1.xml">
		<edmx:Include Alias="Capabilities" Namespace="Org.OData.Capabilities.V1"/>
	</edmx:Reference>
	<edmx:Reference Uri="https://wiki.scn.sap.com/wiki/download/attachments/448470974/Common.xml?api=v2">
		<edmx:Include Alias="Common" Namespace="com.sap.vocabularies.Common.v1"/>
	</edmx:Reference>
	<edmx:Reference Uri="https://wiki.scn.sap.com/wiki/download/attachments/448470971/Communication.xml?api=v2">
		<edmx:Include Alias="vCard" Namespace="com.sap.vocabularies.Communication.v1"/>
	</edmx:Reference>
	<edmx:Reference Uri="http://docs.oasis-open.org/odata/odata/v4.0/errata03/os/complete/vocabularies/Org.OData.Core.V1.xml">
		<edmx:Include Alias="Core" Namespace="Org.OData.Core.V1"/>
	</edmx:Reference>
	<edmx:Reference Uri="http://docs.oasis-open.org/odata/odata/v4.0/errata03/os/complete/vocabularies/Org.OData.Measures.V1.xml">
		<edmx:Include Alias="CQP" Namespace="Org.OData.Measures.V1"/>
	</edmx:Reference>
	<edmx:Reference Uri="https://wiki.scn.sap.com/wiki/download/attachments/448470968/UI.xml?api=v2">
		<edmx:Include Alias="UI" Namespace="com.sap.vocabularies.UI.v1"/>
	</edmx:Reference>
	<edmx:DataServices>
		<Schema xmlns="http://docs.oasis-open.org/odata/ns/edm">
			<Annotations Target="NorthwindModel.Customer">
				<Annotation Term="UI.SelectionFields">
					<Collection>
						<PropertyPath>CustomerID</PropertyPath>
						<PropertyPath>CompanyName</PropertyPath>
					</Collection>
				</Annotation>
				<Annotation Term="UI.LineItem">
					<Collection>
						<Record Type="UI.DataField">
							<PropertyValue Property="Value" Path="CustomerID"/>
						</Record>
						<Record Type="UI.DataField">
							<PropertyValue Property="Value" Path="CompanyName"/>
						</Record>
					</Collection>
				</Annotation>
			</Annotations>
		</Schema>
	</edmx:DataServices>
</edmx:Edmx>

 

14. This is the OVP final result:

 

Debugging the OVP to understand the Generic card concept

Let’s start activating the debug mode in our application. In the UI5 application screen click CTRL + ALT + SHIFT + P, this command opens the Technical Information pop-up and allows the use of the Debug Source. Select only the OVP module, close the pop-up and refresh your browser.

 

SAPUI5 Technical Info:

 

Debug Source:

 

After the browser refresh, open the Chrome Inspector and select Sources in the top menu.

Open the folder resources -> sap -> ovp -> cards. Three folders are loaded under this main folder:

  • generic
  • list
  • loading

 

Notice that only the folders related with the cards used in our application were loaded by the framework.

  • The list folder is available because we used as template for our card.
  • The loading folder contains the Busy Indicator logic during the load of the data.
  • The generic folder is the generic template used by all the OVP cards.

Comparing the files in all the folder we can see a pattern, basically every card folder have at least a Component.js. Inside this file we can check a metadata with the configuration of the card. So let’s compare the Generic and List Components codes to discover more details about the OVP architecture:

Generic Component:

metadata: {
	properties: {
		"contentFragment": {
			"type": "string"
		},
		"headerExtensionFragment": {
			"type": "string"
		},
		"contentPosition": {
			"type": "string",
			"defaultValue": "Middle"
		},
		"footerFragment": {
			"type": "string"
		},
		"identificationAnnotationPath": {
			"type": "string",
			"defaultValue": "com.sap.vocabularies.UI.v1.Identification"
		},
		"selectionAnnotationPath": {
			"type": "string"
		},
		"filters": {
			"type": "object"
		},
		"addODataSelect": {
			"type": "boolean",
			"defaultValue": false
		}
	},
	version: "1.44.11",

	library: "sap.ovp",

	includes: [],

	dependencies: {
		libs: ["sap.m"],
		components: []
	},
	config: {}
},

List Component:

metadata: {
    properties: {
        "contentFragment": {
            "type": "string",
            "defaultValue": "sap.ovp.cards.list.List"
        },
        "annotationPath": {
            "type": "string",
            "defaultValue": "com.sap.vocabularies.UI.v1.LineItem"
        },
        "footerFragment": {
            "type": "string",
            "defaultValue": "sap.ovp.cards.generic.CountFooter"
        },
        "headerExtensionFragment":{
            "type": "string",
            "defaultValue": "sap.ovp.cards.generic.KPIHeader"
        }
    },

    version: "1.44.11",

    library: "sap.ovp",

    includes: [],

    dependencies: {
        libs: [ "sap.m" ],
        components: []
    },
    config: {},
    customizing: {
        "sap.ui.controllerExtensions": {
            "sap.ovp.cards.generic.Card": {
                controllerName: "sap.ovp.cards.list.List"
            }
        }
    }
}

 

We can absorb a few concepts of this code comparison:

  • The properties available in the metadata are the same configured inside the manifest.json.
  • The List Component executes a controller extension of the Generic Component using a new node inside the metadata called customizing.
  • The List Component provides a Fragment XML with the UI5 controls through properties -> contentFragment.

With these concepts in mind we discover that is possible to create a fragment and control the business logic through a controller extension. Let’s put this idea in practice and see how can we generate our custom card.

 

Creating a new Custom card

For this exercise we’re going to create a Button and an event to display a simple message in the controller extension, let’s start creating a new folder cards in the root of the application and inside this folder a new one called mycustomcard.

Inside the folder mycustomcard create 3 files:

  • Component.js (Card controller)
  • MyCustomCard.controller.js (Extension controller)
  • MyCustomCard.fragment.xml (fragment XML)

This should be your application structure after the changes:

 

In the MyCustomCard.fragment.xml, create an UI5 button and associate to an event called “onPressCustomCard”:

<core:FragmentDefinition 
	xmlns:core="sap.ui.core"
	xmlns="sap.m" >
	
	<Button text="{@i18n>MyCustomCardBtn}" press="onPressCustomCard" />
	
</core:FragmentDefinition>

In the MyCustomCard.controller.js, create the method “onPressCustomCard” and place a console log message inside:

(function () {
	"use strict";

	sap.ui.controller("zovpcustomcard.cards.mycustomcard.MyCustomCard", {
		
		onPressCustomCard: function(oEvent) {
			console.log("MyCustomCard - onPressCustomCard");	
		}
		
	});
})();

In the Component.js, create the metadata attribute and configure the contentFragment and the controller extension through the customizing node. Special attention to the  to the sap.ui.declare and sap.ui.require commands in the header, they are responsible for the Generic component load and the declaration of our new Custom Card component:

(function () {
    "use strict";

    jQuery.sap.declare("zovpcustomcard.cards.mycustomcard.Component");
	jQuery.sap.require("sap.ovp.cards.generic.Component");

	sap.ovp.cards.generic.Component.extend("zovpcustomcard.cards.mycustomcard.Component", {
		metadata: {
			properties: {
				"contentFragment": {
					"type": "string",
					"defaultValue": "zovpcustomcard.cards.mycustomcard.MyCustomCard"
				}
			},

			version: "1.44.10",

			library: "sap.ovp",

			includes: [],

			dependencies: {
				libs: ["sap.m"],
				components: []
			},
			config: {},
			customizing: {
				"sap.ui.controllerExtensions": {
					"sap.ovp.cards.generic.Card": {
						controllerName: "zovpcustomcard.cards.mycustomcard.MyCustomCard"
					}
				}
			}
		}
	});
})();

Last step, in the manifest.json, copy the configuration of the List card and adapt the properties to point to the new custom card.

	"sap.ovp": {
		"globalFilterModel": "northwind",
		"globalFilterEntityType": "Customer",
		"cards": {
			"zovpcustomcard_card00": {
				"model": "northwind",
				"template": "sap.ovp.cards.list",
				"settings": {
					"title": "{{zovpcustomcard_card00_title}}",
					"subTitle": "{{zovpcustomcard_card00_subTitle}}",
					"entitySet": "Customers",
					"addODataSelect": "false",
					"annotationPath": "com.sap.vocabularies.UI.v1.LineItem"
				}
			},
			"zovpcustomcard_card01": {
				"model": "northwind",
				"template": "zovpcustomcard.cards.mycustomcard",
				"settings": {
					"title": "{{zovpcustomcard_card01_title}}",
					"subTitle": "{{zovpcustomcard_card01_subTitle}}",
					"entitySet": "Customers"
				}
			}
		}
	}

Don’t forget to place the relevant texts in the i18n file:

zovpcustomcard_card01_title=My Custom Card
zovpcustomcard_card01_subTitle=Just a simple button

MyCustomCardBtn=Click here

 

Execute the application, two cards are displayed now (List and Custom).

 

Click in the button and check the log in the Inspector console:

To report this post you need to login first.

28 Comments

You must be Logged on to comment or reply to a post.

  1. Former Member

    Hi, Felipe!

    Thank you very much for this post, it really helped me!

    Do you know how to change the width of my custom card?

    For example, I need only one card and want it fill all available width.

    As we can see on screenshot below, we can change the width of each card, so it fills twice width. But I can’t find out how to do that.

    Will be very glad to hear your answer, and thank you in advance.

    (1) 
    1. Felipe de Mello Rodrigues Post author

      Hi Yahya,

       

      I never used this functionality before, but since you sent the screenshots I started to search more about the subject.

       

      I’ve started with a research in the SAP Help, but after a debug session in one of my devs I discovered this particular code in the OVP Component.js:

       

      Notice that we have a property called containerLayout responsible for a change in the standard Card Container. I’ve tested this property changing my manifest.json and I was able to resize all my cards. This is the final result:

       

       

       

      Just include this single line of code in your app descriptor and the user will have the option to resize the cards in the way that he wants.

       

      Let me know if you have any questions.

       

      Cheers,

      Felipe

      (2) 
  2. Tanveer Shaikh

    Hi Felipe,

    Thanks for the excellent blog.

    Can you please help with some additional information on Navigation from Cards to other Apps with  data selection/filters ? I saw some documents suggesting use of datafieldforintendbased navigation but I am not able to pass filter/selection parameters to receiver app. Any hint on how to pass filter/selection values to receiver app with while navigation ?

    Thanks,

    Tanveer

    (0) 
    1. Felipe de Mello Rodrigues Post author

      Hi Tanveer,

      Thanks for the feedback!

      DataFieldForIntentBasedNavigation is exactly the annotation you are looking for!

      You can configure this annotation through an ABAP CDS view or directly as a local annotation in your UI5 application. In the example below I create a CDS view with two fields (Company and Plant) and I configure an Intent Based Navigation using the following parameters:

      • Semantic Object: MySemanticObject
      • Action: display
      define view CDS_MyCustomView
        as select from CDS_MyCustomViewTable
      {
            @Consumption.semanticObject: 'MySemanticObject'
            @UI.identification: {
                type: #FOR_INTENT_BASED_NAVIGATION,
                semanticObjectAction: 'display'
            }
            Company,
            
            Plant
      }

      This piece of code will generate the following annotation in the end:

      <Annotation Term="UI.Identification">
        <Collection>
          <Record Type="UI.DataFieldForIntentBasedNavigation">
            <PropertyValue String="MySemanticObject" Property="SemanticObject"/>
            <PropertyValue String="display" Property="Action"/>
            <PropertyValue Property="RequiresContext" Bool="false"/>
          </Record>
        </Collection>
      </Annotation>

      If you don’t use ABAP CDS in your scenario just copy the code above and place inside your Annotation.xml file. You can configure through the Annotation Modeler as well (Web IDE).

      When the user hits the list, the system will collect all the fields from the same Entity Set and append as parameters in the URL (Company and Plant in my example) and execute the navigation to the Semantic Object and Action that we configured before. It will generate an URL like:

      #MySemanticObject-display?Company=XXXX&Plant=YYYY

      Remember to declare your field names using the same name as defined by the Target Application. If the Target is expecting Company it will work perfectly, but if the Target expects BUKRS the filter won’t work properly.

      If you can’t use the same field names in both applications, there is one last option when you include an extra configuration through the Fiori Launchpad Designer. Just search for the Target Mapping configuration of your Target Application and include a new parameter configuration like the one below:

      This configuration will convert the Company field of the URL and place the value inside the field BUKRS.

      Following these tips your navigation and filtering will work fine!

      Cheers,

      Felipe

       

      (0) 
  3. Tanveer Shaikh

    Thanks a lot Felipe,

    This helped a lot and I am able to navigate from Overview page to a list report /Analytic list page  !!!  I am using Hana XSodata with local annotations, and its work just fine using DataFieldForIntentBasedNavigation in Webide Annotation modeler.

    Have a follow up question – Can we use same annotations to navigate from a line item of a list report or Analytic list page to some other app? For Example If I have list report for all Sales Order for a customer , built using Fiori element template and webide annotation modeler, and from the line items of the list report I want to navigate to a Sales Order tracking app using the Sales order number from the list report line item.

    Tried to look for some documentation and looks like need to extent the list report + local annotation to achieve that ?

    Can you please point in the right direction to look for  ? Do we need extension or just local annotation can achieve it ? My setup is same Using webide annotation modeler with Hana xsodata as backend data source. So, no ABAP CDS.

    Thanks,

    Tanveer

    (0) 
    1. Felipe de Mello Rodrigues Post author

      Hi Tanveer,

      I think the best option is to reuse the annotation DataFieldForIntentBasedNavigation in one of the fields contained inside your ListItem annotation, this way the List Report will generate a link for the field like the example below (check the column Document Number):

      If you still need to use the item navigation for this purpose you will probably need to extend your List Report.

      Cheers,

      Felipe

      (0) 
  4. Tanveer Shaikh

    Hi Felipe,

    You are awesome ! your replies helped a lot !

    I stumbled at one more point – Is there way to change font size and color on a card using local annotations ? or any other way ?

    Thanks,

    Tanveer

    (0) 
    1. Felipe de Mello Rodrigues Post author

      Hi Tanveer,

      I never heard about changes in the font-size through annotations, about color there is only an option to change the color of the Data Point using an annotation called criticality.

      I’m currently working in a new blog post to demonstrate this functionality, probably I release this content until the end of this month.

      PS: I would like to ask you to post your future questions in the QA instead of using blog comments, this way other users can benefit about these particular scenarios. Just send me a message after you publish your question and I’ll try to provide my solutions about the subject.

      Thanks!

      Felipe

      (0) 
      1. Tanveer Shaikh

        Thanks Felipe !

        I posted a question in Q&A section, did not any helpful response. But sure will follow.

        Anyways – I was able to change font and color using CSS resource. Not sure if its a perfect solution but it works !

        Thanks,

        Tanveer

        (0) 
        1. Felipe de Mello Rodrigues Post author

          Hi Tanveer,

          Changes in the CSS are not advised by SAP because there is a risk to create impacts in the UI5 standard behaviour, but if this is the only way to achieve your solution just make sure to test with different browsers and different screen resolutions to avoid unexpected problems in the future.

          Cheers,

          Felipe

          (0) 
  5. Maksym Berezin

    Hi, Felipe!

     

    I have tried out your example and it seem a little bit different. I get a problem if I use the setting “entitySet” by the second card in the manifest.json. Can you help me?

    Thanks,

    Max

    (0) 
    1. Felipe de Mello Rodrigues Post author

      Hi Max,

      I didn’t understand exactly the issue, you commented about a problem in the second card, but in the image I notice a problem loading the data of the first card (standard template).

      I advise you to have a look in your console log to troubleshoot the error, looks like you’ve missed some configuration in the manifest.json, review the configuration of your OData service and your model as well.

      Cheers,

      Felipe

      (0) 
    1. Felipe de Mello Rodrigues Post author

      Hi Max,

      I created this application using the version 1.44 back in May of 2017, since then SAP has been releasing several new versions and some impacts can appear with new releases.

      I’ve tested my original application and there is actually an error happening with the List card (standard template), but the Custom card continues to work fine, you can check your console log with messages for the events onInit and onPressCustomCard working fine.

      If you want to use UI5 latest version I advise to create your Overview Page project from the scratch using Web IDE template and just adapt the custom card codes for your new project.

      In the future I will try to update this post with adaptation tips for new versions. Anyways, thanks for the advice and let me know if you need more info.

      Cheers,

      Felipe

      (0) 
  6. Goga Didebashvili

    Hello Felipe, this is a really helpful post and information.

    I have one question. We have developed a UI5 application and we want to use Fiori OVP as the homepage with some informative dashboards/cards.  But the OVP and our App should be in one environment, so which one would be the right and legitimate approach:

    a) Place our app and OVP in a fiori launchpad.

    b) Availability to navigate to our UI5 app FROM the OVP.

    in case b) , which card/element/control should I use to open a different application from the OVP. and how would the navigation be implemented ?

    (0) 
    1. Felipe de Mello Rodrigues Post author

      Hi Goga,

      You should actually provide navigation to your end application through the Fiori Launchpad and also through the OVP application.

      Overview Pages are just applications that help the user to discover what to act on next in a specific domain. SAP defines this concept as “Street level view”, take a look in the image below:

      If you have any questions about the purpose of OVP apps, I advise you to have a quick look in the following post: https://blogs.sap.com/2015/10/25/introducing-sap-fiori-overview-page-card-based-information-visualization/

      Cheers,

      Felipe

      (0) 
  7. Former Member

    Hi,

    Is it possible to add multiple custom cards in overview page ? if so then how I can configure multiple fragments in component.js file.

    Regards,

    Mriganka Basak

    (0) 
  8. Former Member

    Hi Felipe,

    Thanks for your suggestion.Its wrk fine for me..But now I am facing new issue ,the overview application running properly locally but it is not working when I deployed it in hana cloud platform.

    Need  your input on the same.

    Thanks in advance.

    Regards,

    Mriganka

    (0) 
    1. Felipe de Mello Rodrigues Post author

      Hi Mriganka,

      It’s quite difficult to define a root cause without any logs, I would suggest first to compare the SAPUI5 versions and have a look in the Development Tools in your web browser.

      Also, since this in an issue non-related with the main subject of the article I would suggest you to create a question in the Q&A section, this way other users can provide their inputs. Just remember to provide the maximum information you can about the issue (e.g. message logs, UI5 version, etc).

      Cheers,

      Felipe

      (0) 
  9. Aakanksha Gupta

    Hi @Felipe

    Great blog. It worked for me.

     

    Need some more help from you.

    Actually I am trying to create a donut chart using the same approach.

     

    So, below are the added changes that I did to achieve this functionality.

    1. Added my odata service in the project using New->oData Service option.

    For me I had created a simple odata service consisting the below details.

     

    2. Added the annotation file to project using New->Annotation File.

    For me, no annotation files are present for now in abap based cds view.

    3. Donut chart code in CustomCard.fragment.xml file.

    Added the vizFrame chart code in CustomCard.fragment.xml file.

     

    4. The added odata service is set to the default model in manifest.json file.

    5. Setting the entity set and the fields in the vizframe code of the CustomCard.fragment.xml file.

    6. Also added the relevant model and entityset in the card as well.

     

    After doing these all changes, still my card shows Cannot load card.

    Please suggest as to what exactly I had missed or wrongly added to achieve this funtionality.

     

     

    Kindly help.

     

    This is the metadata code for my service.

    <edmx:Edmx xmlns:edmx="http://schemas.microsoft.com/ado/2007/06/edmx"
    	xmlns:m="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata" xmlns:sap="http://www.sap.com/Protocols/SAPData" Version="1.0">
    	<edmx:Reference xmlns:edmx="http://docs.oasis-open.org/odata/ns/edmx"
    		Uri="http://192.168.139.61:8000/sap/opu/odata/IWFND/CATALOGSERVICE;v=2/Vocabularies(TechnicalName='%2FIWBEP%2FVOC_COMMON',Version='0001',SAP__Origin='LOCAL')/$value"><edmx:Include Namespace="com.sap.vocabularies.Common.v1" Alias="Common"/></edmx:Reference>
    	<edmx:DataServices m:DataServiceVersion="2.0">
    		<Schema xmlns="http://schemas.microsoft.com/ado/2008/09/edm" Namespace="ZVBAK_CDS_CDS" xml:lang="en" sap:schema-version="1">
    			<EntityType Name="ZVBAK_CDSType" sap:label="Info Provider Interface View for VBAK table" sap:content-version="1">
    				<Key><PropertyRef Name="ORDERTYPE"/></Key><Property Name="ORDERTYPE" Type="Edm.String" Nullable="false" MaxLength="4" sap:display-format="UpperCase" sap:label="Sales document type"
    					sap:quickinfo="Sales Document Type"/><Property Name="NETPRICE" Type="Edm.Decimal" Precision="16" Scale="3"/></EntityType>
    			<EntityContainer Name="ZVBAK_CDS_CDS_Entities" m:IsDefaultEntityContainer="true" sap:supported-formats="atom json xlsx"><EntitySet Name="ZVBAK_CDS" EntityType="ZVBAK_CDS_CDS.ZVBAK_CDSType" sap:creatable="false" sap:updatable="false" sap:deletable="false"
    				sap:content-version="1"/></EntityContainer><atom:link xmlns:atom="http://www.w3.org/2005/Atom" rel="self" href="http://192.168.139.61:8000/sap/opu/odata/sap/ZVBAK_CDS_CDS/$metadata"/><atom:link xmlns:atom="http://www.w3.org/2005/Atom" rel="latest-version"
    				href="http://192.168.139.61:8000/sap/opu/odata/sap/ZVBAK_CDS_CDS/$metadata"/></Schema>
    	</edmx:DataServices>
    </edmx:Edmx>

    Thanks,

    Aakanksha

     

    (0) 
    1. Felipe de Mello Rodrigues Post author

      Hi Aakanksha Gupta,

      There is no need to create a custom card for a donut chart, you can create a standard Analytical Card and configure your chart based on annotations.

      Have a look in the SAP Fiori Guidelines, there is a section dedicated for this requirement: https://experience.sap.com/fiori-design-web/analytical-card/#donut-chart

      You can search the SAP Help Portal for more information about technical details and implementation.

      Cheers,

      Felipe Rodrigues

      (0) 
      1. Aakanksha Gupta

        Thanks  @Felipe for replying.

        Actually I am working on one such requirement only(have to dispaly donut chart for my data on on overview page).

        I tried using cds views. I could successfully write data to a table, list.

        For chart, I created an analytical ABAP based CDS view, but while adding the analyical card to the template, KPI annotation path was blank for my case.

        And as the KPI annotation path is the mandatory field while adding an analytical card, so I am unable to add that card to my template.

         

         

        I even tried adding the KPI header using the annotation model.

        But still for the cases tried, I am getting Cannot upload data on the card.

         

        Due to these failed attempts with CDS VIEWS and analytical card, I tried using custom cards on overview pages.

         

         

        Thanks,

        Aakanksha

         

         

        cds view code.

        @AbapCatalog.sqlViewName: 'ZOVFSO_DCHART'
        @AbapCatalog.compiler.compareFilter: true
        @AccessControl.authorizationCheck: #NOT_REQUIRED
        @EndUserText.label: 'Sales Order Donut Chart'
        //@VDM.viewType: #CONSUMPTION
        @OData.publish: true
        @Analytics.dataExtraction.enabled
        @Analytics.query: true
        
        @UI.chart: {
            title: 'Gross Amount by Customer',
            description: 'Donut-chart displaying the gross amount by customer',
            chartType: #DONUT,
            dimensions: [ 'ORDERTYPE' ],  -- Reference to one element
            measures: [ 'NETPRICE' ]     -- Reference to one or more elements
        }
        
        
        define view ZSO_DONUTCHART as select from I_SalesOrder{
         
          @AnalyticsDetails.query.axis: #ROWS
           I_SalesOrder.SalesOrderType as ORDERTYPE,
         
         @AnalyticsDetails.query.axis: #COLUMNS
        // @DefaultAggregation: #SUM
           I_SalesOrder.TotalNetAmount as NETPRICE
           
        ////@Semantics.amount: 'true'
        ////   @DefaultAggregation: #SUM
        //  ZVBAK_CDS.
        //// count(distinct VBAk.vbeln ) as TOTALORDTYPES
         
        }
        
        

        This is the metadata file for the odata service created.

        <?xml version="1.0" encoding="UTF-8"?>
        
        -<edmx:Edmx xmlns:sap="http://www.sap.com/Protocols/SAPData" xmlns:m="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata" xmlns:edmx="http://schemas.microsoft.com/ado/2007/06/edmx" Version="1.0">
        
        
        -<edmx:DataServices m:DataServiceVersion="2.0">
        
        
        -<Schema xml:lang="en" xmlns="http://schemas.microsoft.com/ado/2008/09/edm" sap:schema-version="1" Namespace="ZSO_DONUTCHART_CDS">
        
        
        -<EntityType sap:content-version="1" sap:semantics="aggregate" sap:label="Sales Order Donut Chart" Name="ZSO_DONUTCHARTType">
        
        
        -<Key>
        
        <PropertyRef Name="ID"/>
        
        </Key>
        
        <Property Name="ID" sap:sortable="false" sap:updatable="false" sap:filterable="false" Nullable="false" Type="Edm.String"/>
        
        <Property Name="TotaledProperties" sap:sortable="false" sap:updatable="false" Type="Edm.String" sap:is-annotation="true" sap:aggregation-role="totaled-properties-list"/>
        
        <Property sap:label="Sales document type" Name="ORDERTYPE" sap:updatable="false" Type="Edm.String" sap:aggregation-role="dimension" sap:creatable="false" MaxLength="4"/>
        
        <Property sap:label="Net Value" Name="NETPRICE" sap:updatable="false" sap:filterable="false" Type="Edm.Decimal" sap:aggregation-role="measure" sap:creatable="false" sap:unit="NETPRICE_E" sap:text="NETPRICE_F" Scale="2" Precision="42"/>
        
        <Property sap:label="Net Value (Formatted)" Name="NETPRICE_F" sap:updatable="false" sap:filterable="false" Type="Edm.String" sap:creatable="false" MaxLength="60"/>
        
        <Property sap:semantics="currency-code" sap:label="Net Value (Currency)" Name="NETPRICE_E" sap:updatable="false" sap:filterable="false" Type="Edm.String" sap:creatable="false" MaxLength="5"/>
        
        </EntityType>
        
        
        -<EntityType sap:content-version="1" Name="ODataQueryAdditionalMetadata">
        
        
        -<Key>
        
        <PropertyRef Name="ODataQueryMetadata"/>
        
        </Key>
        
        <Property Name="ODataQueryMetadata" sap:sortable="false" sap:updatable="false" sap:filterable="false" Nullable="false" Type="Edm.String" sap:creatable="false"/>
        
        <Property Name="ODataQueryMetadataValue_Current" sap:sortable="false" sap:updatable="false" sap:filterable="false" Type="Edm.String" sap:creatable="false"/>
        
        <Property Name="ODataQueryMetadataValueAtDefine" sap:sortable="false" sap:updatable="false" sap:filterable="false" Type="Edm.String" sap:creatable="false"/>
        
        </EntityType>
        
        
        -<EntityContainer Name="ZSO_DONUTCHART_CDS_Entities" sap:supported-formats="atom json xlsx" m:IsDefaultEntityContainer="true">
        
        <EntitySet sap:content-version="1" Name="ZSO_DONUTCHART" sap:updatable="false" sap:creatable="false" sap:deletable="false" EntityType="ZSO_DONUTCHART_CDS.ZSO_DONUTCHARTType"/>
        
        <EntitySet sap:content-version="1" Name="AdditionalMetadata" sap:updatable="false" sap:creatable="false" sap:deletable="false" EntityType="ZSO_DONUTCHART_CDS.ODataQueryAdditionalMetadata"/>
        
        </EntityContainer>
        
        <atom:link xmlns:atom="http://www.w3.org/2005/Atom" href="http://s4appl1.hitachiconsulting.net:8000/sap/opu/odata/sap/ZSO_DONUTCHART_CDS/$metadata" rel="self"/>
        
        <atom:link xmlns:atom="http://www.w3.org/2005/Atom" href="http://s4appl1.hitachiconsulting.net:8000/sap/opu/odata/sap/ZSO_DONUTCHART_CDS/$metadata" rel="latest-version"/>
        
        </Schema>
        
        </edmx:DataServices>
        
        </edmx:Edmx>
        (0) 
        1. Felipe de Mello Rodrigues Post author

          Hi Aakanksha Gupta,

          You need to configure a Data Point to configure a KPI header, all of this information is available through SAP Help Portal. Have a look in the following links:

          Also, have a look in one of my articles explaining how to Create an Analytical List Page using ABAP CDS views and annotations. This post is not focused on the Overview Page development but I create an Analytical Card with a KPI header for the Weight of Luggage.

          This article uses ABAP CDS views in the back-end and I you can notice the use of @DataPoint annotation.

          Cheers,

          Felipe Rodrigues

          (0) 

Leave a Reply