はじめまして、テラスカイの范です。
SalesforceのB2B Commerce はデフォルトの標準設定のまますぐに使用することができますが、多くの場合、拡張が必要になります。
管理パッケージであるこのアプリケーションの動作を変更するには、カスタムコードを使用して拡張と上書きを行いますが、今回はB2BCommerceの標準ページネーションを拡張する方法を紹介します。
B2B Commerceの概要については、下記の記事をご参照ください。
SalesforceのB2B Commerce はデフォルトの標準設定のまますぐに使用することができますが、多くの場合、拡張が必要になります。
管理パッケージであるこのアプリケーションの動作を変更するには、カスタムコードを使用して拡張と上書きを行いますが、今回はB2BCommerceの標準ページネーションを拡張する方法を紹介します。
B2B Commerceの概要については、下記の記事をご参照ください。
B2B Commerceで企業にもB2C体験を!<B2B Commerceの概要をご紹介します>
2019年2月に日本版がリリースされたB2B Commerceを紹介します。
B2B Commerceで何ができる?<商品管理編>
B2B Commerceの商品管理方法について紹介します。
はじめに
B2B Commerceのテクノロジースタックを簡単に説明します。
B2BCommerceはユーザーインターフェイスを備えたJavaScriptに広く依存しています。基本的に、次のテクノロジースタックに基づいて構築されています。
- jQuery (base, UI, and validation)
- Backbone
- Bootstrap
- Handlebars
他のライブラリも使用されますが、これらの4つはアーキテクチャの中核を形成します。
ページネーションを実装する前に、以下の手順で商品一覧メニューを作成します。
1、サブスクライバーページを作成します。Visualforceページ名は「productList」とします。
2、サブスクライバーページにメニューリンクを追加します。
3、CC管理でメニューキャッシュを更新します。
これで商品一覧ページの準備ができたので、さっそくページネーションの実装に入ります。
1、サブスクライバーページを作成します。Visualforceページ名は「productList」とします。
2、サブスクライバーページにメニューリンクを追加します。
3、CC管理でメニューキャッシュを更新します。
これで商品一覧ページの準備ができたので、さっそくページネーションの実装に入ります。
実装
まずはページネーションのコンポネントを用意します。
ページネーションのビューとテンプレートはB2BCommerceの標準のものをそのままで利用します。
ページネーションのビューとテンプレートはB2BCommerceの標準のものをそのままで利用します。
<apex:component > <apex:attribute name="eLName" type="String" description="DOM object name"/> <script type="text/javascript"> jQuery(function($) { CCRZ.views.paginationView = CCRZ.CloudCrazeView.extend({ templateDesktop: CCRZ.util.template('paginationTmpl'), desktopEl: '{!eLName}', events: { 'click .firstAction': 'firstPage', 'click .lastAction': 'lastPage', 'click .previousAction': 'previousPage', 'click .nextAction': 'nextPage', 'click .gotoPage': 'gotoPage', 'change .sizeAction': 'changePageSize', 'click .resortAction': 'resort' }, init: function () { this.listenTo(this.model, 'reset', this.render); }, hostRendered: function (context, options) { if (options) { this.hostView = options.hostView; } this.render(); }, withinViewChange: false, managedSubView: true, preViewChanged: function () { this.withinViewChanged = true; }, preRender: function () { this.$el.html(''); v = this; v.model.state.slidingWindowSize = parseInt(CCRZ.getPageConfig('pgbl.WndSz', '3')); v.model.state.currentSlidingWindow = Math.floor((v.model.state.currentPage - 1) / v.model.state.slidingWindowSize) + 1; v.model.state.startPage = (v.model.state.currentSlidingWindow - 1) * v.model.state.slidingWindowSize + 1; if ((v.model.state.currentSlidingWindow * v.model.state.slidingWindowSize) <= v.model.state.totalPages) { v.model.state.endPage = (v.model.state.currentSlidingWindow) * v.model.state.slidingWindowSize; } else { v.model.state.endPage = v.model.state.totalPages; } v.model.state.hasPrevious = v.model.hasPreviousPage(); v.model.state.hasNext = v.model.hasNextPage(); v.model.state.startItem = (v.model.state.currentPage - 1) * v.model.state.pageSize + 1; if ((v.model.state.currentPage * v.model.state.pageSize) <= v.model.state.totalRecords) { v.model.state.endItem = (v.model.state.currentPage) * v.model.state.pageSize; } else { v.model.state.endItem = v.model.state.totalRecords; } var itemsPerPage = CCRZ.getPageConfig('pgbl.itmPerP', '10,25,50,75'); v.model.state.itemsPerPagePLValues = itemsPerPage.split(","); for (var i = 0; i < v.model.state.itemsPerPagePLValues.length; i++) { v.model.state.itemsPerPagePLValues[i] = parseInt(v.model.state.itemsPerPagePLValues[i], 10); } }, renderDesktop: function () { v.setElement($(this.desktopEl)); v.$el.html(v.templateDesktop(v.model.state)); }, postRender: function () { if (!this.withinViewChanged && this.hostView) { var eventName = 'pagination:' + this.hostView + ':rendered'; CCRZ.pubSub.trigger(eventName, this); CCRZ.console.log('trigger=' + eventName + ' context=' + this); } this.withinViewChanged = false; }, firstPage: function () { this.model.getFirstPage(); }, previousPage: function () { this.model.getPreviousPage(); }, nextPage: function () { this.model.getNextPage(); }, lastPage: function () { this.model.getLastPage(); }, setSorting: function (sortKey, asc) { this.model.setSorting(sortKey, asc); this.model.fullCollection.sort(); }, gotoPage: function (event) { var pageNum = $(event.target).data('id'); this.model.getPage(pageNum); }, changePageSize: function (event) { v = this; var pSize = parseInt($(event.currentTarget).val()); v.model.setPageSize(pSize, { first: true }); }, resort: function (event) { } }); }); </script> <script id="paginationTmpl" type="text/template"> <div class="panel panel-default cc_panel cc_paginator"> <div class="panel-body cc_body"> <div class="row"> <div class="col-xs-4"> <p class="cc_paginator_legend"> {{pageLabelMap 'PaginatorItems'}} {{startItem}} - {{endItem}} {{pageLabelMap 'PaginatorOf'}} {{totalRecords}} {{pageLabelMap 'PaginatorTotal'}} </p> </div> <div class="col-xs-4"> <div class="text-center cc_current_page"> {{pageLabelMap 'PaginatorPage'}} {{#if hasPrevious}} <a href="#" class="firstAction cc_first_action">{{pageLabelMap 'PaginatorFirst'}}</a> <a href="#" class="previousAction pageAction cc_page_action">{{pageLabelMap 'PaginatorPrevious'}}</a> {{/if}} {{#for startPage endPage 1}} {{#ifEquals this ../currentPage}} {{safeQuote this}} {{else}} <a href="#" class="gotoPage cc_goto_page" data-id="{{safeQuote this}}">{{safeQuote this}}</a> {{/ifEquals}} {{/for}} {{#if hasNext}} <a href="#" class="nextAction pageAction cc_page_action">{{pageLabelMap 'PaginatorNext'}}</a> <a href="#" class="lastAction cc_last_action">{{pageLabelMap 'PaginatorLast'}}</a> {{/if}} </div> </div> <div class="col-xs-4"> <div class="form-inline cc_form-inline cc_paginator_form pull-right"> <label for="itemsPerPage" class="cc_items_per_page"> {{pageLabelMap 'PaginatorShow'}} <select id="itemsPerPage" class="form-control input-sm sizeAction cc_size_action"> {{#each this.itemsPerPagePLValues}} <option value="{{safeQuote this}}" {{#ifEquals ../pageSize this}} selected {{/ifEquals}}>{{safeQuote this}}</option> {{/each}} </select> {{pageLabelMap 'PaginatorPerPage'}} </label> </div> </div> </div> </div> </div> </script> </apex:component>
pagination.component
次に商品一覧のVisualforceページを実装します。
※1 ページネーションを利用する際に、CloudCrazePageableからの拡張が必要です。
※2 modeは「server」「client」「infinite」がありますが、今回は「client」を指定します。
※3 stateはすべてのページネーション状態を格納するコンテナオブジェクトです。「firstPage」と「pageSize」プロパティーはそれぞれ、1と10を設定します。
※4 リモートアクションでコントローラーの「searchProduct」メソッドを呼び出し、商品一覧レコードを取得します。
※1 ページネーションを利用する際に、CloudCrazePageableからの拡張が必要です。
※2 modeは「server」「client」「infinite」がありますが、今回は「client」を指定します。
※3 stateはすべてのページネーション状態を格納するコンテナオブジェクトです。「firstPage」と「pageSize」プロパティーはそれぞれ、1と10を設定します。
※4 リモートアクションでコントローラーの「searchProduct」メソッドを呼び出し、商品一覧レコードを取得します。
<apex:page docType="html-5.0" sidebar="false" showHeader="false" standardStylesheets="false" applyHtmlTag="false" controller="ProductListCtrl"> <c:pagination eLName=".paginator"/> <div class="paginator"></div> <div class="productList"></div> <script type="text/javascript"> jQuery(function($) { var productListCollection = CCRZ.CloudCrazePageable.extend({ //※1 mode: 'client', //※2 silent: false, state: { //※3 firstPage: 1, pageSize: 10 }, className: 'ProductListCtrl', fetchAllNavData: function (state, formdata, callback) { this.invokeCtx('searchProduct', function (res) { //※4 callback(res.data); }, { buffer: false, nmsp: false }); } }); var productlistView = CCRZ.CloudCrazeView.extend({ templateDesktop: CCRZ.util.template('productListTmpl'), init: function () { var v = this; v.coll = new productListCollection(); var paginationView = new CCRZ.views.paginationView({ model: v.coll }); this.listenTo(v.coll, 'reset', this.ready); paginationView.listenTo( v.coll, 'pagination:host:rendered', paginationView.hostRendered ); this.generateDisplay(v.coll, function () { v.render(); }); }, generateDisplay: function (coll, callback) { coll.fetch({ success: function () { if (_.isFunction(callback)) { callback(); } } }); }, ready: function (dataList, args) { this.coll = dataList; this.render(); }, render: function () { var v = this; v.setElement('.productList'); v.$el.html(v.templateDesktop(v.coll.toJSON())); } }); new productlistView(); }); </script> <script id="productListTmpl" type="text/template"> <table class="table table-striped"> <tr> <th>SKU</th> <th>名前</th> <th>開始日</th> <th>終了日</th> <th>商品種別</th> <th>ステータス</th> <th>商品インデックス状況</th> </tr> {{#each this}} <tr> <td>{{ccrz__SKU__c}}</td> <td>{{Name}}</td> <td>{{date ccrz__StartDate__c}}</td> <td>{{date ccrz__EndDate__c}}</td> <td>{{ccrz__ProductType__c}}</td> <td>{{ccrz__ProductStatus__c}}</td> <td>{{ccrz__ProductIndexStatus__c}}</td> </tr> {{/each}} </table> </script> </apex:page>
productList.page
結果
もしナビゲーションのスタイルを変更したいという場合には、Bootstrapのpaginationを参考にしていただければ、ナビゲーションのスタイルも変えられると思います。
おわりに
ライブラリを使わずに、標準ページネーションとテンプレートを利用することで、ページネーションを作りましたが、いかがでしょうか。みなさんのB2B Commerceカスタマイズ開発に、お役に立てれば幸いです。
最後まで読んでいただきましてありがとうござした。
最後まで読んでいただきましてありがとうござした。
18 件