The following steps explain creating a React SPA Container component (eaem-sites-spa-dm-video-container/components/container) extending Core Container component (core/wcm/components/container/v1/container) for Video Backgrounds and Component (eg. text) overlays...
For creating a simple SPA navigation app check this post. For product sample check adobe documentation
For configuring Dynamic Media check this post
Demo | Package Install | Github
Dynamic Media Configuration
Sync Configuration at Folder Level
Set Dynamic Media Video Profile
Video Renditions (Encodes)
Component Dialog
View as Published
Solution
<%@include file="/libs/granite/ui/global.jsp"%>
<%@page session="false"
import="org.apache.sling.commons.json.JSONObject"%>
<%@ page import="org.apache.sling.api.SlingHttpServletRequest" %>
<%@ page import="com.day.cq.dam.api.Asset" %>
<%@ page import="com.day.cq.dam.api.renditions.DynamicMediaRenditionProvider" %>
<%@ page import="com.day.cq.dam.api.Rendition" %>
<%@ page import="java.util.HashMap" %>
<%@ page import="java.util.List" %>
<%
response.setContentType("application/json");
SlingHttpServletRequest eaemSlingRequest = slingRequest;
String contentPath = eaemSlingRequest.getRequestPathInfo().getSuffix();
Resource currentResource = eaemSlingRequest.getResourceResolver().getResource(contentPath);
Asset asset = (currentResource != null ? currentResource.adaptTo(Asset.class) : null);
JSONObject dynRenditions = new JSONObject();
if( (asset == null) || !(asset.getMimeType().startsWith("video/")) || (asset.getMetadata("dam:scene7ID") == null)) {
dynRenditions.write(response.getWriter());
return;
}
DynamicMediaRenditionProvider dmRendProvider = sling.getService(DynamicMediaRenditionProvider.class);
String s7Domain = String.valueOf(asset.getMetadata("dam:scene7Domain"));
String scene7FileAvs = String.valueOf(asset.getMetadata("dam:scene7FileAvs"));
HashMap<String, Object> rules = new HashMap<String, Object>();
rules.put("remote", true);
rules.put("video", true);
List<Rendition> dmRenditions = dmRendProvider.getRenditions(asset, rules);
JSONObject dynRendition = new JSONObject();
String image = null, avsName = scene7FileAvs.substring(scene7FileAvs.lastIndexOf("/") + 1);
dynRendition.put("url", getScene7Url(s7Domain, scene7FileAvs));
dynRendition.put("image", getRendThumbnail(s7Domain, scene7FileAvs));
dynRendition.put("name", avsName);
dynRenditions.put(avsName, dynRendition);
for (Rendition dmRendition : dmRenditions) {
dynRendition = new JSONObject();
image = dmRendition.getPath();
if(image.endsWith(".mp4")){
image = image.substring(0, image.lastIndexOf(".mp4"));
}
dynRendition.put("name", dmRendition.getName());
dynRendition.put("image", getRendThumbnail(s7Domain, image));
dynRendition.put("url", getScene7Url(s7Domain, dmRendition.getPath()));
dynRenditions.put(dmRendition.getName(), dynRendition);
}
dynRenditions.write(response.getWriter());
%>
<%!
private static String getScene7Url(String s7Domain, String rendPath){
return s7Domain + "/s7viewers/html5/VideoViewer.html?asset=" + rendPath;
}
private static String getRendThumbnail(String s7Domain, String rendPath){
return s7Domain + "/is/image/" + rendPath + "?fit=constrain,1&wid=200&hei=200";
}
%>
5) Create file (nt:file) /apps/eaem-sites-spa-dm-video-container/clientlibs/clientlib-dmvideo/js.txt, add
spa-dmvideo.js
6) Create file (nt:file) /apps/eaem-sites-spa-dm-video-container/clientlibs/clientlib-dmvideo/spa-dmvideo.js, add the following code...
(function ($, $document) {
var DM_VIDEO_FIELD = "./eaemDMVideo",
ENCODE_SELECT = "./eaemDMEncode",
DM_VIDEO_RENDS_URL = "/apps/eaem-sites-spa-dm-video-container/video-dyn-renditions/content.html";
$document.on('dialog-ready', handleVideoField);
function handleVideoField(){
var $videoField = $("foundation-autocomplete[name='" + DM_VIDEO_FIELD + "']");
if(_.isEmpty($videoField)){
return;
}
setSelectedEncode($videoField.val());
$videoField.on("change", addEncodes);
}
function addEncodes(event){
var $encodeField = $("coral-select[name='" + ENCODE_SELECT + "']"),
selVideoPath = event.target.value;
if(_.isEmpty(selVideoPath) || _.isEmpty($encodeField)){
return;
}
$encodeField.find("coral-select-item").not("[value='NONE']").remove();
loadEncodesInSelect(selVideoPath);
}
function getCoralSelectItem(text, value, selected){
return '<coral-select-item value="' + value + '" ' + selected + '>' + text + '</coral-select-item>';
}
function loadEncodesInSelect(videoPath, selectedValue){
var $encodeField = $("coral-select[name='" + ENCODE_SELECT + "']");
$.ajax(DM_VIDEO_RENDS_URL + videoPath).done(function(renditions){
_.each(renditions,function(rendition){
$encodeField.append(getCoralSelectItem(rendition.name, rendition.name,
((selectedValue == rendition.name) ? "selected" : "")));
});
});
}
function setSelectedEncode(selVideoPath){
if(!selVideoPath){
return;
}
var dialogPath;
try{
dialogPath = Granite.author.DialogFrame.currentDialog.editable.slingPath;
}catch(err){
console.log("Error getting dialog path...", err);
}
if(!dialogPath){
return;
}
$.ajax(dialogPath).done(function(data){
var dmEncode = data[ENCODE_SELECT.substr(2)];
if(!dmEncode){
return;
}
loadEncodesInSelect(selVideoPath, dmEncode);
})
}
}(jQuery, jQuery(document)));
import React from 'react';
import {MapTo, withComponentMappingContext, Container, ResponsiveGrid, ComponentMapping} from '@adobe/cq-react-editable-components';
import {Helmet} from "react-helmet";
class EAEMContainer extends Container {
get containerProps() {
let containerProps = super.containerProps;
containerProps.style = {
"width": '100%',
"height": '500px'
};
return containerProps;
}
get videoDivProps() {
return {
"id": "eaem-dm-video-viewer",
"style": {
"zIndex": "0",
"position": "relative"
}
};
}
get overlayDivProps() {
return {
"style" : {
...{
"position": "absolute",
"zIndex": "1"
} ,
...this.props.overlayDivStyle
}
};
}
componentDidMount() {
const timer = setInterval((() => {
if(window.s7viewers){
clearInterval(timer);
this.loadVideo()
}
}).bind(this), 500);
}
loadVideo(){
new window.s7viewers.VideoViewer({
"containerId": "eaem-dm-video-viewer",
"params": {
"asset": this.props.dmVideoEncode,
"serverurl": this.props.dmServerUrl,
"videoserverurl": this.props.dmVideoServerUrl
}
}).init();
}
render() {
return (
<div {...this.containerProps}>
{ this.props.dmVideoPath &&
<Helmet>
<script src={ this.props.dmVideoViewerPath }></script>
</Helmet>
}
{ this.props.dmVideoPath &&
<div {...this.videoDivProps}>
<div {...this.overlayDivProps}>
{ this.childComponents }
{ this.placeholderComponent }
</div>
</div>
}
{ !this.props.dmVideoPath &&
<div>
{ this.childComponents }
{ this.placeholderComponent }
</div>
}
</div>
);
}
}
export default MapTo('eaem-sites-spa-dm-video-container/components/container')(EAEMContainer);
14) Add the following code in com.eaem.core.models.impl.EAEMDMVideoContainerModelImpl.
package com.eaem.core.models.impl;
import com.adobe.cq.export.json.ContainerExporter;
import com.day.cq.dam.api.Asset;
import com.day.cq.wcm.foundation.model.responsivegrid.ResponsiveGrid;
import com.eaem.core.models.EAEMDMVideoContainerModelExporter;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import org.apache.commons.lang3.StringUtils;
import org.apache.sling.api.SlingHttpServletRequest;
import com.adobe.cq.export.json.ComponentExporter;
import javax.annotation.PostConstruct;
import org.apache.sling.api.resource.Resource;
import org.apache.sling.api.resource.ResourceResolver;
import org.apache.sling.api.resource.ValueMap;
import org.apache.sling.models.annotations.Exporter;
import org.apache.sling.models.annotations.Model;
import org.apache.sling.models.annotations.injectorspecific.InjectionStrategy;
import org.apache.sling.models.annotations.injectorspecific.ScriptVariable;
import org.apache.sling.models.annotations.injectorspecific.ValueMapValue;
import java.util.HashMap;
import java.util.Map;
@Model(
adaptables = {SlingHttpServletRequest.class},
adapters = {ContainerExporter.class, ComponentExporter.class},
resourceType = {"eaem-sites-spa-dm-video-container/components/container"}
)
@Exporter(
name = "jackson",
extensions = {"json"}
)
@JsonSerialize(as = EAEMDMVideoContainerModelExporter.class)
public class EAEMDMVideoContainerModelImpl extends ResponsiveGrid implements EAEMDMVideoContainerModelExporter{
@ScriptVariable
private Resource resource;
@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL)
private String eaemDMVideo;
@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL)
private String eaemDMEncode;
private Map<String, Object> metadata;
@PostConstruct
protected void initModel() {
super.initModel();
if( (this.resource == null) || StringUtils.isEmpty(eaemDMVideo)) {
return;
}
ResourceResolver resolver = this.resource.getResourceResolver();
Resource videoRes = resolver.getResource(eaemDMVideo);
if(videoRes == null){
return;
}
metadata = videoRes.adaptTo(Asset.class).getMetadata();
}
public String getDmAccountName(){
if(metadata == null){
return "";
}
String fileName = String.valueOf(metadata.get("dam:scene7File"));
if(StringUtils.isEmpty(fileName)){
return "";
}
return fileName.substring(0, fileName.indexOf("/"));
}
public String getDmServerUrl() {
if(metadata == null){
return "";
}
return metadata.get("dam:scene7Domain") + "is/image/";
}
public String getDmVideoViewerPath() {
if(metadata == null){
return "";
}
return metadata.get("dam:scene7Domain") + "s7viewers/html5/js/VideoViewer.js";
}
public String getDmVideoServerUrl() {
if(metadata == null){
return "";
}
return metadata.get("dam:scene7Domain") + "is/content/";
}
public Map<String, String> getOverlayDivStyle() {
Map<String, String> divStyles = new HashMap<String, String>();
ValueMap vm = this.resource.getValueMap();
divStyles.put("top" , vm.get("overlayTop", ""));
divStyles.put("left" , vm.get("overlayLeft", ""));
divStyles.put("backgroundColor" , vm.get("overlayBGColor", "#FFFFFF"));
divStyles.put("padding" , vm.get("overlayPadding", "10px 20px 10px 20px"));
return divStyles;
}
public String getDmVideoPath() {
return eaemDMVideo;
}
public String getDmVideoEncode() {
return getDmAccountName() + "/" + eaemDMEncode;
}
}











No comments:
Post a Comment