AppSurvey.vue 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  1. <template>
  2. <ui-card
  3. v-if="modalState.show"
  4. class="fixed bottom-8 right-8 shadow-2xl border-2 w-72 group"
  5. >
  6. <button
  7. class="absolute bg-white shadow-md rounded-full -right-2 -top-2 transition scale-0 group-hover:scale-100"
  8. @click="closeModal"
  9. >
  10. <v-remixicon class="text-gray-600" name="riCloseLine" />
  11. </button>
  12. <h2 class="font-semibold text-lg">
  13. {{ activeModal.title }}
  14. </h2>
  15. <p class="mt-1 dark:text-gray-100 text-gray-700">
  16. {{ activeModal.body }}
  17. </p>
  18. <div class="space-y-2 mt-4">
  19. <ui-button
  20. :href="activeModal.url"
  21. tag="a"
  22. target="_blank"
  23. rel="noopener"
  24. class="w-full block"
  25. variant="accent"
  26. >
  27. {{ activeModal.button }}
  28. </ui-button>
  29. </div>
  30. </ui-card>
  31. </template>
  32. <script setup>
  33. import { shallowReactive, computed, onMounted } from 'vue';
  34. import browser from 'webextension-polyfill';
  35. import dayjs from '@/lib/dayjs';
  36. const modalTypes = {
  37. testimonial: {
  38. title: 'Hi There 👋',
  39. body: 'Thank you for using Automa, and if you have a great experience. Would you like to give us a testimonial?',
  40. button: 'Give Testimonial',
  41. url: 'https://testimonial.to/automa',
  42. },
  43. survey: {
  44. title: "How do you think we're doing?",
  45. body: 'To help us make Automa as best it can be, we need a few minutes of your time to get your feedback.',
  46. button: 'Take Survey',
  47. url: 'https://www.automa.site/survey',
  48. },
  49. };
  50. const modalState = shallowReactive({
  51. show: true,
  52. type: 'survey',
  53. });
  54. function closeModal() {
  55. let value = true;
  56. if (modalState.type === 'survey') {
  57. value = new Date().toString();
  58. }
  59. modalState.show = false;
  60. localStorage.setItem(`has-${modalState.type}`, value);
  61. }
  62. async function checkModal() {
  63. try {
  64. const { isFirstTime } = await browser.storage.local.get('isFirstTime');
  65. if (isFirstTime) {
  66. modalState.show = false;
  67. localStorage.setItem('has-testimonial', true);
  68. localStorage.setItem('has-survey', Date.now());
  69. return;
  70. }
  71. const survey = localStorage.getItem('has-survey');
  72. if (!survey) return;
  73. const daysDiff = dayjs().diff(survey, 'day');
  74. const showTestimonial =
  75. daysDiff >= 2 && !localStorage.getItem('has-testimonial');
  76. if (showTestimonial) {
  77. modalState.show = true;
  78. modalState.type = 'testimonial';
  79. } else {
  80. modalState.show = false;
  81. }
  82. } catch (error) {
  83. console.error(error);
  84. }
  85. }
  86. const activeModal = computed(() => modalTypes[modalState.type]);
  87. onMounted(checkModal);
  88. </script>