function basename(path) {
if (!path) {
return "";
}
return path.substring(path.lastIndexOf("/") + 1);
}
jQuery(document).ready(function ($) {
const $feedbackHTML = `
We are always looking for ways to improve & would love to have a any valuable feedback from our customers. Please contact us to submit any query/feedback.
Contact Us
`;
// handle media selection
function handleMediaSelection(mediaUploader, previewContainer, cb) {
return function () {
const attachment = mediaUploader
.state()
.get("selection")
.first()
.toJSON();
// create preview element
const previewElement = previewContainer.find(".preview-element");
// display preview
previewElement.html(`
File Name: ${attachment.filename}
Remove
`);
// save attachment ID
const attachmentInput = previewContainer.find("input");
previewContainer.find(".select-button").hide();
attachmentInput.val(attachment.url).trigger("change");
if (cb) {
cb(attachment);
}
};
}
// handle remove button click
function handleRemoveButtonClick() {
const previewContainer = $(this)
.closest(".media-input-container")
.find(".preview-container");
previewContainer.find(".preview-element").empty();
previewContainer.find("input").val("").trigger("change");
previewContainer.find(".select-button").show();
return false;
}
// handle media uploader click
function handleMediaUploaderClick() {
const previewContainer = $(this)
.closest(".media-input-container")
.find(".preview-container");
// create media uploader
const mediaUploader = wp.media({
title: "Select a file",
button: { text: "Select" },
multiple: false,
});
// handle media selection
mediaUploader.on(
"select",
handleMediaSelection(mediaUploader, previewContainer)
);
// open media uploader when button is clicked
mediaUploader.open();
return false;
}
// handle remove button click
$("body").on(
"click",
".media-input-container .remove-button",
handleRemoveButtonClick
);
// handle media uploader click
$("body").on(
"click",
".media-input-container .select-button",
handleMediaUploaderClick
);
const loadModel = () => {
$modelPreview = document.getElementById("ar-model-viewer-admin-preview");
let variantsCreated = false;
$modelPreview.addEventListener("load", function () {
console.log("model loaded");
const $dataObject = window.arModelViewerSettings || {};
if ($dataObject.plan === "premium") {
const $value = $dataObject.arVariants;
const { name, value } = $value;
if (!value) {
return;
}
if (!variantsCreated) {
variantsCreated = true;
clearAllVariants();
const variants = Object.values(value);
variants.sort((a, b) => (a.display_order < b.display_order ? -1 : 1));
for (let i = 0; i < variants.length; i++) {
createVariant(variants[i], false);
}
}
}
});
};
const variantForm = () => {
if (!isPremiumPlan()) {
return "";
}
return `
Variants
Add Variant
Remove All Variants
`;
};
const updateModelAttribute = ($attr, $value) => {
$("#ar-model-viewer-admin-preview").attr($attr, $value);
};
const renderInitialWithSettings = ($dataObject) => {
if ($dataObject) {
for (const $d of Object.keys($dataObject)) {
updateUI($dataObject[$d]);
}
}
};
const mediaInputContainer = (src, name, containerId) => {
style = "";
if (src) {
style = "display:none";
}
return `
`;
};
const isOptionSelected = (option, selected) =>
option == selected ? "selected" : "";
const selectInputContainer = (value, name, title, options, containerId) => {
const renderInput = (option, name) => {
return `${name} `;
};
$outputHTML = `${title}
`;
$outputHTML += ``;
for (const o of options) {
$outputHTML += renderInput(o.value, o.name);
}
$outputHTML += " ";
return $outputHTML;
};
const handleCheckboxContainer = (value, name, title, option, containerId) => {
const checked = value === "true" ? "checked" : "";
$outputHTML = `${title}
${option}
`;
return $outputHTML;
};
const handle3DModelInput = ($value) => {
const postMetaBox = $("#ar-features-listings");
$outputHTML = '3D Model
';
const { url, name } = $value;
const selector = `input[name=${name}]`;
$("body").on("change", selector, function (e) {
const {value} = e.target
updateModelAttribute("src", value);
});
$outputHTML += mediaInputContainer(url, name, "ar-model-media");
postMetaBox.append(`${$outputHTML} `);
};
const handleIosModelInput = ($value) => {
const postMetaBox = $("#ar-features-listings");
$outputHTML = 'iOS Supported Model
';
$outputHTML +=
'Select USDZ model which will be used on supported iOS 12+ devices via AR Quick Look on Safari.
';
const { url, id, name } = $value;
$outputHTML += mediaInputContainer(url, name, "ar-ios-model-media");
const selector = `input[name=${name}]`;
$("body").on("change", selector, function (e) {
const {value} = e.target
updateModelAttribute("ios-src", value);
});
postMetaBox.append(`${$outputHTML} `);
};
const handleARPlacement = ($value) => {
const postMetaBox = $("#ar-features-listings");
const options = [
{ value: "floor", name: "Floor" },
{ value: "wall", name: "Wall" },
];
const { value: v, name } = $value;
$outputHTML = selectInputContainer(
v,
name,
"AR Placement",
options,
"ar-placement-select"
);
$("body").on("change", "#ar-placement-select", function (e) {
e.preventDefault();
e.stopPropagation();
$(`input[name="${name}"`).val(e.target.value);
updateModelAttribute("ar-placement", e.target.value);
});
postMetaBox.append(`${$outputHTML} `);
};
const handleSkyBoxImage = ($value) => {
const postMetaBox = $("#ar-features-listings");
const { url, name } = $value;
$outputHTML = 'SkyBox Bg Image
';
$outputHTML += mediaInputContainer(url, name, "ar-skybox-image");
postMetaBox.append(`${$outputHTML} `);
const selector = `input[name=${name}]`;
$("body").on("change", selector, function (e) {
const {value} = e.target
updateModelAttribute("skybox-image", value);
});
};
const handlePosterImage = ($value) => {
const postMetaBox = $("#ar-features-listings");
const { url, name } = $value;
$outputHTML = 'Poster Image
';
$outputHTML += mediaInputContainer(url, name, "ar-poster-image");
postMetaBox.append(`${$outputHTML} `);
const selector = `input[name=${name}]`;
$("body").on("change", selector, function (e) {
const {value} = e.target
updateModelAttribute("poster", value);
});
};
const handleAutoRotateOption = ($value) => {
const { name, value } = $value;
const postMetaBox = $("#ar-features-listings");
$outputHTML = handleCheckboxContainer(
value,
name,
"Auto Rotate 3D Model",
"Enable"
);
postMetaBox.append(`${$outputHTML} `);
const selector = `input[name=${name}]`;
$("body").on("change", selector, function (e) {
updateModelAttribute(
"auto-rotate",
e.target.checked == "true" ? "true" : ""
);
});
};
const handleLockScale = ($value) => {
const { name, value } = $value;
const postMetaBox = $("#ar-features-listings");
$outputHTML = handleCheckboxContainer(
value == "fixed" ? "true" : "false",
name,
"AR Lock Scaling",
"Enable"
);
postMetaBox.append(`${$outputHTML} `);
const selector = `input[name=${name}]`;
$("body").on("change", selector, function (e) {
updateModelAttribute(
"ar-scale",
e.target.checked == "true" ? "fixed" : "auto"
);
});
};
const updateUI = ($value) => {
if (!$value) {
return;
}
const { name } = $value;
switch (name) {
case "ar_model_viewer_file":
handle3DModelInput($value);
break;
case "ar_model_viewer_file_ios":
handleIosModelInput($value);
break;
case "ar_placement_model":
handleARPlacement($value);
break;
case "ar_model_viewer_skybox_image":
handleSkyBoxImage($value);
break;
case "ar_model_viewer_poster_image":
handlePosterImage($value);
break;
case "ar_model_rotate":
handleAutoRotateOption($value);
break;
case "ar_model_scaling_lock":
handleLockScale($value);
break;
case "ar_variants": {
return;
}
default:
}
};
function createMaterial(m, name, variantCount, variantBody) {
if (!m) {
m = {
color: "",
texture: "",
texture_url: "",
};
}
const material = $('
');
const materialHeader = $(
``
);
material.append(materialHeader);
const materialBody = $('
');
material.append(materialBody);
const materialOptions = $('
');
const colorInput = $(
`Material Color
`
);
materialOptions.append(colorInput);
const textureOption = $('
');
textureOption.append("Material Texture ");
const imageInput = mediaInputContainer(
m.texture_url,
m.texture,
`ar_variant[${variantCount}][materials][${name}][texture]`,
"variant-" + variantCount + "material-" + name
);
// const imageInput = $(' ');
textureOption.append(imageInput);
materialOptions.append(textureOption);
materialBody.append(materialOptions);
materialHeader.on("click", function () {
if (materialBody.hasClass("active")) {
materialBody.slideUp().removeClass("active");
} else {
variantBody.find(".material-body").slideUp().removeClass("active");
materialBody.slideDown().addClass("active");
}
});
material.find(".material-delete").on("click", function () {
material.remove();
});
variantBody.append(material);
materialHeader.trigger("click");
}
let variantIndex = 0;
function createModelMaterialsOptions(
model,
materials,
variantCount,
variantBody
) {
const index = variantCount;
if (!materials) {
materials = [];
}
variantBody.find(".material-form").remove();
variantBody.find(".material").remove();
const modelMaterials = model.model.materials || [];
const materialForm = $("
");
const selectId = "variant-" + index + "material-select";
$input = selectInputContainer(
"",
"",
"Material",
modelMaterials.map((a) => ({ name: a.name, value: a.name })),
selectId
);
materialForm.append($input);
const addMaterialButton = $(
"Add "
);
materialForm.append(addMaterialButton);
variantBody.append(materialForm);
addMaterialButton.on("click", function () {
const materialOption = $("#" + selectId).find(":selected");
createMaterial(null, materialOption.text(), index, variantBody);
return false;
});
if (materials) {
for (const m of Object.keys(materials)) {
createMaterial(materials[m], m, index, variantBody);
}
}
}
function createVariant(obj = {}, autoOpen = true) {
let { name, desc, materials, modelSrc } = obj;
if (!desc) {
desc = "";
}
variantIndex++;
const index = variantIndex;
if (!name) {
name = "Variant " + index;
}
const variant = $(`
`);
const variantName = name;
const variantHeader = $(
``
);
variant.append(variantHeader);
const variantBody = $('
');
const variantNameInput = $(
`Name
`
);
variantBody.append(variantNameInput);
const variantDescInput = $(
`Description
`
);
variantBody.append(variantDescInput);
variant.append(variantBody);
const $modelOption =
'Variant 3D Model (Optional)
';
variantBody.append($modelOption);
const inputName = `ar_variant[${index}][modelSrc]`;
const selector = `input[name="${inputName}"]`;
const modelId = "variant-" + index + "-model-viewer";
const modelImgId = "variant-" + index + "-model-src";
const modelViewer = $(
" "
).hide();
variantBody.append(modelViewer);
variantBody.append(
'' +
mediaInputContainer(modelSrc, inputName, modelImgId) +
"
"
);
$("body").on("change", selector, function (e) {
console.log("trigger change");
const {value} = e.target
if (value) {
modelViewer.attr("src", value).show();
} else {
modelViewer.attr('src', '').hide();
createModelMaterialsOptions($modelPreview, [], index, variantBody);
}
});
modelViewer.on("load", function () {
console.log("variant model loaded");
if (modelSrc === modelViewer.attr("src")) {
createModelMaterialsOptions(
modelViewer[0],
materials,
index,
variantBody
);
} else {
createModelMaterialsOptions(modelViewer[0], [], index, variantBody);
}
});
if (modelSrc) {
modelViewer.attr("src", modelSrc).show();
} else {
createModelMaterialsOptions($modelPreview, materials, index, variantBody);
}
variantHeader.on("click", function () {
variantBody.slideToggle();
});
variant.find(".variant-delete").on("click", function () {
variant.remove();
});
if (!autoOpen) {
variantBody.slideUp();
}
$("#variant-container").append(variant);
return variant;
}
function clearAllVariants() {
console.log("delete all variants");
$("#variant-container .variant").find(".variant-delete").trigger("click");
}
function isPremiumPlan() {
return window.arModelViewerSettings.plan === "premium";
}
function initVariants() {
$("#variant-container").sortable({
handle: ".variant-header",
axis: "y",
containment: "#variant-container",
tolerance: "pointer",
});
$("#add-variant").on("click", function () {
const variant = createVariant();
return false;
});
$("#delete-all-variants").on("click", function () {
clearAllVariants();
return false;
});
}
function initPostMetaBox() {
const $postMetaBox = $("#ar-model-viewer-post-metabox");
if (!$postMetaBox.length) {
return;
}
$postMetaBox.append(
`
${$feedbackHTML}`
);
const $dataObject = window.arModelViewerSettings || {};
renderInitialWithSettings($dataObject);
const listings = $("#ar-features-listings");
listings.append(`${variantForm()}`);
initVariants();
}
initPostMetaBox();
if (window.arModelViewerSettings) {
$modelPreview = document.getElementById(
window.arModelViewerSettings.modelId
);
if (!$modelPreview) {
return;
}
loadModel();
}
});