add recorder events
This commit is contained in:
parent
b55f2e98ea
commit
abd0a03cd0
3 changed files with 31 additions and 1 deletions
|
|
@ -15,6 +15,7 @@ import { TRPCClientError } from "@trpc/client";
|
||||||
import { useAtom } from "jotai/index";
|
import { useAtom } from "jotai/index";
|
||||||
import paywallAtom from "~/atoms/paywallAtom";
|
import paywallAtom from "~/atoms/paywallAtom";
|
||||||
import recordVideoModalOpen from "~/atoms/recordVideoModalOpen";
|
import recordVideoModalOpen from "~/atoms/recordVideoModalOpen";
|
||||||
|
import { usePostHog } from "posthog-js/react";
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
closeModal: () => void;
|
closeModal: () => void;
|
||||||
|
|
@ -45,6 +46,7 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
const [duration, setDuration] = useState<number>(0);
|
const [duration, setDuration] = useState<number>(0);
|
||||||
const [, setPaywallOpen] = useAtom(paywallAtom);
|
const [, setPaywallOpen] = useAtom(paywallAtom);
|
||||||
const videoRef = useRef<null | HTMLVideoElement>(null);
|
const videoRef = useRef<null | HTMLVideoElement>(null);
|
||||||
|
const posthog = usePostHog();
|
||||||
|
|
||||||
const handleRecording = async () => {
|
const handleRecording = async () => {
|
||||||
const screenStream = await navigator.mediaDevices.getDisplayMedia({
|
const screenStream = await navigator.mediaDevices.getDisplayMedia({
|
||||||
|
|
@ -80,6 +82,8 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
recorderRef.current.startRecording();
|
recorderRef.current.startRecording();
|
||||||
|
|
||||||
setStep("in");
|
setStep("in");
|
||||||
|
|
||||||
|
posthog?.capture("recorder: start video recording");
|
||||||
};
|
};
|
||||||
|
|
||||||
const handleStop = () => {
|
const handleStop = () => {
|
||||||
|
|
@ -98,6 +102,8 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
});
|
});
|
||||||
|
|
||||||
setStep("post");
|
setStep("post");
|
||||||
|
|
||||||
|
posthog?.capture("recorder: video recording finished");
|
||||||
};
|
};
|
||||||
|
|
||||||
const handleDelete = () => {
|
const handleDelete = () => {
|
||||||
|
|
@ -109,6 +115,8 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
|
|
||||||
closeModal();
|
closeModal();
|
||||||
setStep("pre");
|
setStep("pre");
|
||||||
|
|
||||||
|
posthog?.capture("recorder: video deleted");
|
||||||
};
|
};
|
||||||
|
|
||||||
const handlePause = () => {
|
const handlePause = () => {
|
||||||
|
|
@ -119,6 +127,7 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
} else {
|
} else {
|
||||||
recorderRef.current.pauseRecording();
|
recorderRef.current.pauseRecording();
|
||||||
}
|
}
|
||||||
|
posthog?.capture("recorder: recording paused/resumed", { pause });
|
||||||
setPause(!pause);
|
setPause(!pause);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
@ -146,6 +155,8 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
"Recording - " + dayjs().format("D MMM YYYY") + ".webm";
|
"Recording - " + dayjs().format("D MMM YYYY") + ".webm";
|
||||||
invokeSaveAsDialog(blob, dateString);
|
invokeSaveAsDialog(blob, dateString);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
posthog?.capture("recorder: video downloaded");
|
||||||
};
|
};
|
||||||
|
|
||||||
const generateThumbnail = async (video: HTMLVideoElement) => {
|
const generateThumbnail = async (video: HTMLVideoElement) => {
|
||||||
|
|
@ -187,6 +198,7 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
.then(() => {
|
.then(() => {
|
||||||
void router.push("share/" + id);
|
void router.push("share/" + id);
|
||||||
setRecordOpen(false);
|
setRecordOpen(false);
|
||||||
|
posthog?.capture("recorder: video uploaded");
|
||||||
})
|
})
|
||||||
.catch((err) => {
|
.catch((err) => {
|
||||||
console.error(err);
|
console.error(err);
|
||||||
|
|
@ -197,6 +209,7 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
err.message ===
|
err.message ===
|
||||||
"Sorry, you have reached the maximum video upload limit on our free tier. Please upgrade to upload more."
|
"Sorry, you have reached the maximum video upload limit on our free tier. Please upgrade to upload more."
|
||||||
) {
|
) {
|
||||||
|
posthog?.capture("recorder: video upload paywall hit");
|
||||||
setPaywallOpen(true);
|
setPaywallOpen(true);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -325,6 +338,8 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
<video
|
<video
|
||||||
src={URL.createObjectURL(blob)}
|
src={URL.createObjectURL(blob)}
|
||||||
controls
|
controls
|
||||||
|
onPlay={() => posthog?.capture("recorder: played preview video")}
|
||||||
|
onPause={() => posthog?.capture("recorder: paused preview video")}
|
||||||
ref={videoRef}
|
ref={videoRef}
|
||||||
className="mb-4 w-[75vw]"
|
className="mb-4 w-[75vw]"
|
||||||
/>
|
/>
|
||||||
|
|
@ -374,7 +389,10 @@ export default function Recorder({ closeModal, step, setStep }: Props) {
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
className="ml-auto inline-flex items-center rounded-md bg-indigo-500 px-4 py-2 text-sm font-semibold leading-6 text-white shadow transition duration-150 ease-in-out hover:bg-indigo-400 disabled:cursor-not-allowed"
|
className="ml-auto inline-flex items-center rounded-md bg-indigo-500 px-4 py-2 text-sm font-semibold leading-6 text-white shadow transition duration-150 ease-in-out hover:bg-indigo-400 disabled:cursor-not-allowed"
|
||||||
onClick={() => void closeModal()}
|
onClick={() => {
|
||||||
|
posthog?.capture("recorder: closed post-modal");
|
||||||
|
void closeModal();
|
||||||
|
}}
|
||||||
>
|
>
|
||||||
Close
|
Close
|
||||||
</button>
|
</button>
|
||||||
|
|
|
||||||
|
|
@ -4,10 +4,12 @@ const Recorder = dynamic(() => import("~/components/Recorder"), { ssr: false });
|
||||||
import dynamic from "next/dynamic";
|
import dynamic from "next/dynamic";
|
||||||
import { useAtom } from "jotai";
|
import { useAtom } from "jotai";
|
||||||
import recordVideoModalOpen from "~/atoms/recordVideoModalOpen";
|
import recordVideoModalOpen from "~/atoms/recordVideoModalOpen";
|
||||||
|
import { usePostHog } from "posthog-js/react";
|
||||||
|
|
||||||
export default function VideoRecordModal() {
|
export default function VideoRecordModal() {
|
||||||
const [open, setOpen] = useAtom(recordVideoModalOpen);
|
const [open, setOpen] = useAtom(recordVideoModalOpen);
|
||||||
const [step, setStep] = useState<"pre" | "in" | "post">("pre");
|
const [step, setStep] = useState<"pre" | "in" | "post">("pre");
|
||||||
|
const posthog = usePostHog();
|
||||||
|
|
||||||
function closeModal() {
|
function closeModal() {
|
||||||
setOpen(false);
|
setOpen(false);
|
||||||
|
|
@ -15,6 +17,8 @@ export default function VideoRecordModal() {
|
||||||
|
|
||||||
const handleClose = () => {
|
const handleClose = () => {
|
||||||
if (step === "pre") closeModal();
|
if (step === "pre") closeModal();
|
||||||
|
|
||||||
|
posthog?.capture("cancel video pre-recording");
|
||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|
|
||||||
|
|
@ -5,6 +5,8 @@ import axios from "axios";
|
||||||
import { useRouter } from "next/router";
|
import { useRouter } from "next/router";
|
||||||
import { useAtom } from "jotai";
|
import { useAtom } from "jotai";
|
||||||
import uploadVideoModalOpen from "~/atoms/uploadVideoModalOpen";
|
import uploadVideoModalOpen from "~/atoms/uploadVideoModalOpen";
|
||||||
|
import { usePostHog } from "posthog-js/react";
|
||||||
|
import { useSession } from "next-auth/react";
|
||||||
|
|
||||||
export default function VideoUploadModal() {
|
export default function VideoUploadModal() {
|
||||||
const [open, setOpen] = useAtom(uploadVideoModalOpen);
|
const [open, setOpen] = useAtom(uploadVideoModalOpen);
|
||||||
|
|
@ -14,6 +16,8 @@ export default function VideoUploadModal() {
|
||||||
const getSignedUrl = api.video.getUploadUrl.useMutation();
|
const getSignedUrl = api.video.getUploadUrl.useMutation();
|
||||||
const apiUtils = api.useContext();
|
const apiUtils = api.useContext();
|
||||||
const videoRef = useRef<null | HTMLVideoElement>(null);
|
const videoRef = useRef<null | HTMLVideoElement>(null);
|
||||||
|
const posthog = usePostHog();
|
||||||
|
const { data: session } = useSession();
|
||||||
|
|
||||||
const handleFileChange = (e: ChangeEvent<HTMLInputElement>): void => {
|
const handleFileChange = (e: ChangeEvent<HTMLInputElement>): void => {
|
||||||
if (e.target.files) {
|
if (e.target.files) {
|
||||||
|
|
@ -33,6 +37,10 @@ export default function VideoUploadModal() {
|
||||||
|
|
||||||
function closeModal() {
|
function closeModal() {
|
||||||
setOpen(false);
|
setOpen(false);
|
||||||
|
|
||||||
|
posthog?.capture("cancel video upload", {
|
||||||
|
stripeSubscriptionStatus: session?.user.stripeSubscriptionStatus,
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
const handleSubmit = async (): Promise<void> => {
|
const handleSubmit = async (): Promise<void> => {
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue