3813 | © 2025 BOSS海投助手 | Yangshengzhou 版权所有
3814 |
3815 | `;
3816 |
3817 | envelopeBack.addEventListener("click", () => {
3818 | envelope.style.transform = "rotateY(180deg)";
3819 | setTimeout(() => {
3820 | const content = document.getElementById("letter-content");
3821 | if (content) {
3822 | content.style.display = "block";
3823 | content.style.animation = "fadeInUp 0.5s ease-out forwards";
3824 | }
3825 | }, 300);
3826 | });
3827 |
3828 | const envelopeFront = document.createElement("div");
3829 | envelopeFront.id = "envelope-front";
3830 | envelopeFront.style.cssText = `
3831 | position: absolute;
3832 | width: 100%;
3833 | height: 100%;
3834 | background: #fff;
3835 | border-radius: 10px;
3836 | box-shadow: 0 15px 35px rgba(0,0,0,0.2);
3837 | transform: rotateY(180deg);
3838 | backface-visibility: hidden;
3839 | display: flex;
3840 | flex-direction: column;
3841 | `;
3842 |
3843 | const titleBar = document.createElement("div");
3844 | titleBar.style.cssText = `
3845 | padding: 20px 30px;
3846 | background: linear-gradient(135deg, ${COLORS.primary}, ${COLORS.primaryDark});
3847 | color: white;
3848 | font-size: clamp(1.2rem, 2.5vw, 1.4rem);
3849 | font-weight: 600;
3850 | border-radius: 10px 10px 0 0;
3851 | display: flex;
3852 | align-items: center;
3853 | `;
3854 | titleBar.innerHTML = `
3872 |
你好,未来的成功人士:
3873 |
展信如晤。
3874 |
3875 | 我是Yangshengzhou,我曾经和你一样在求职路上反复碰壁。
3876 | 简历石沉大海、面试邀约寥寥、沟通效率低下...于是我做了这个小工具。
3877 |
3878 |
3879 | 现在,我将它分享给你,希望能够帮到你:
3880 |
3881 |
3882 | - 自动沟通页面岗位,一键打招呼
3883 | - AI智能回复HR提问,24小时在线不错过任何机会
3884 | - 个性化沟通策略,大幅提升面试邀约率
3885 |
3886 |
3887 | 工具只是辅助,你的能力才是核心竞争力。
3888 | 愿它成为你求职路上的得力助手,助你斩获Offer!
3889 |
3890 |
3891 | 冀以尘雾之微补益山海,荧烛末光增辉日月。
3892 |
3893 |
3894 | 如果插件对你有帮助,请给她点个 Star🌟!
3895 |
3896 |
3897 |
4134 |
${
4135 | step.content
4136 | }
4137 |
4138 | ${buttonsHtml}
4139 | `;
4140 |
4141 | if (stepIndex === this.steps.length - 1) {
4142 | document
4143 | .getElementById("guide-finish-btn")
4144 | .addEventListener("click", () => this.endGuide(true));
4145 | } else {
4146 | document
4147 | .getElementById("guide-next-btn")
4148 | .addEventListener("click", () => this.nextStep());
4149 | document
4150 | .getElementById("guide-skip-btn")
4151 | .addEventListener("click", () => this.endGuide());
4152 | }
4153 |
4154 | if (stepIndex === this.steps.length - 1) {
4155 | const finishBtn = document.getElementById("guide-finish-btn");
4156 | finishBtn.addEventListener("mouseenter", () => {
4157 | finishBtn.style.background = this.darkenColor(
4158 | step.highlightColor || "#4285f4",
4159 | 15
4160 | );
4161 | finishBtn.style.boxShadow =
4162 | "0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -1px rgba(0, 0, 0, 0.06)";
4163 | });
4164 | finishBtn.addEventListener("mouseleave", () => {
4165 | finishBtn.style.background = step.highlightColor || "#4285f4";
4166 | finishBtn.style.boxShadow =
4167 | "0 1px 3px 0 rgba(0, 0, 0, 0.1), 0 1px 2px 0 rgba(0, 0, 0, 0.06)";
4168 | });
4169 | } else {
4170 | const nextBtn = document.getElementById("guide-next-btn");
4171 | const skipBtn = document.getElementById("guide-skip-btn");
4172 |
4173 | nextBtn.addEventListener("mouseenter", () => {
4174 | nextBtn.style.background = this.darkenColor(
4175 | step.highlightColor || "#4285f4",
4176 | 15
4177 | );
4178 | nextBtn.style.boxShadow =
4179 | "0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -1px rgba(0, 0, 0, 0.06)";
4180 | });
4181 | nextBtn.addEventListener("mouseleave", () => {
4182 | nextBtn.style.background = step.highlightColor || "#4285f4";
4183 | nextBtn.style.boxShadow =
4184 | "0 1px 3px 0 rgba(0, 0, 0, 0.1), 0 1px 2px 0 rgba(0, 0, 0, 0.06)";
4185 | });
4186 |
4187 | skipBtn.addEventListener("mouseenter", () => {
4188 | skipBtn.style.background = "#f3f4f6";
4189 | });
4190 | skipBtn.addEventListener("mouseleave", () => {
4191 | skipBtn.style.background = "white";
4192 | });
4193 | }
4194 |
4195 | this.guideElement.style.opacity = "1";
4196 | this.guideElement.style.transform = "translateY(0)";
4197 | },
4198 |
4199 | setGuidePositionFromTarget(step, rect) {
4200 | let left, top;
4201 | const guideWidth = 320;
4202 | const guideHeight = 240;
4203 |
4204 | switch (step.arrowPosition) {
4205 | case "top":
4206 | left = rect.left + rect.width / 2 - guideWidth / 2;
4207 | top = rect.top - guideHeight - 20;
4208 | break;
4209 | case "bottom":
4210 | left = rect.left + rect.width / 2 - guideWidth / 2;
4211 | top = rect.bottom + 20;
4212 | break;
4213 | case "left":
4214 | left = rect.left - guideWidth - 20;
4215 | top = rect.top + rect.height / 2 - guideHeight / 2;
4216 | break;
4217 | case "right":
4218 | left = rect.right + 20;
4219 | top = rect.top + rect.height / 2 - guideHeight / 2;
4220 | break;
4221 | default:
4222 | left = rect.right + 20;
4223 | top = rect.top;
4224 | }
4225 |
4226 | left = Math.max(10, Math.min(left, window.innerWidth - guideWidth - 10));
4227 | top = Math.max(10, Math.min(top, window.innerHeight - guideHeight - 10));
4228 |
4229 | this.guideElement.style.left = `${left}px`;
4230 | this.guideElement.style.top = `${top}px`;
4231 | this.guideElement.style.transform = "translateY(0)";
4232 | },
4233 |
4234 | setGuidePositionFromDefault(step) {
4235 | const position = step.defaultPosition || {
4236 | left: "50%",
4237 | top: "50%",
4238 | transform: "translate(-50%, -50%)",
4239 | };
4240 |
4241 | Object.assign(this.guideElement.style, {
4242 | left: position.left,
4243 | top: position.top,
4244 | right: position.right || "auto",
4245 | bottom: position.bottom || "auto",
4246 | transform: position.transform || "none",
4247 | });
4248 | },
4249 |
4250 | nextStep() {
4251 | const currentStep = this.steps[this.currentStep];
4252 | if (currentStep) {
4253 | const target = document.querySelector(currentStep.target);
4254 | if (target) {
4255 | target.removeEventListener("click", this.nextStep);
4256 | }
4257 | }
4258 |
4259 | this.currentStep++;
4260 | if (this.currentStep < this.steps.length) {
4261 | this.guideElement.style.opacity = "0";
4262 | this.guideElement.style.transform = "translateY(10px)";
4263 |
4264 | setTimeout(() => {
4265 | this.showStep(this.currentStep);
4266 | }, 300);
4267 | } else {
4268 | }
4269 | },
4270 |
4271 | clearHighlights() {
4272 | this.highlightElements.forEach((el) => el.remove());
4273 | this.highlightElements = [];
4274 | },
4275 |
4276 | endGuide(isCompleted = false) {
4277 | this.clearHighlights();
4278 |
4279 | this.guideElement.style.opacity = "0";
4280 | this.guideElement.style.transform = "translateY(10px)";
4281 | this.overlay.style.opacity = "0";
4282 |
4283 | setTimeout(() => {
4284 | if (this.overlay && this.overlay.parentNode) {
4285 | this.overlay.parentNode.removeChild(this.overlay);
4286 | }
4287 | if (this.guideElement && this.guideElement.parentNode) {
4288 | this.guideElement.parentNode.removeChild(this.guideElement);
4289 | }
4290 |
4291 | if (isCompleted && this.chatUrl) {
4292 | window.open(this.chatUrl, "_blank");
4293 | }
4294 | }, 300);
4295 |
4296 | document.dispatchEvent(new Event("guideEnd"));
4297 | },
4298 |
4299 | darkenColor(color, percent) {
4300 | let R = parseInt(color.substring(1, 3), 16);
4301 | let G = parseInt(color.substring(3, 5), 16);
4302 | let B = parseInt(color.substring(5, 7), 16);
4303 |
4304 | R = parseInt((R * (100 - percent)) / 100);
4305 | G = parseInt((G * (100 - percent)) / 100);
4306 | B = parseInt((B * (100 - percent)) / 100);
4307 |
4308 | R = R < 255 ? R : 255;
4309 | G = G < 255 ? G : 255;
4310 | B = B < 255 ? B : 255;
4311 |
4312 | R = Math.round(R);
4313 | G = Math.round(G);
4314 | B = Math.round(B);
4315 |
4316 | const RR =
4317 | R.toString(16).length === 1 ? "0" + R.toString(16) : R.toString(16);
4318 | const GG =
4319 | G.toString(16).length === 1 ? "0" + G.toString(16) : G.toString(16);
4320 | const BB =
4321 | B.toString(16).length === 1 ? "0" + B.toString(16) : B.toString(16);
4322 |
4323 | return `#${RR}${GG}${BB}`;
4324 | },
4325 | };
4326 |
4327 | const style = document.createElement("style");
4328 | style.textContent = `
4329 | @keyframes guide-pulse {
4330 | 0% { transform: scale(1); box-shadow: 0 0 0 0 rgba(66, 133, 244, 0.4); }
4331 | 70% { transform: scale(1); box-shadow: 0 0 0 10px rgba(66, 133, 244, 0); }
4332 | 100% { transform: scale(1); box-shadow: 0 0 0 0 rgba(66, 133, 244, 0); }
4333 | }
4334 |
4335 | .guide-content .highlight {
4336 | font-weight: 700;
4337 | color: #1a73e8;
4338 | }
4339 |
4340 | .guide-content .warning {
4341 | font-weight: 700;
4342 | color: #d93025;
4343 | }
4344 | `;
4345 | document.head.appendChild(style);
4346 |
4347 | const STORAGE = {
4348 | LETTER: "letterLastShown",
4349 | GUIDE: "shouldShowGuide",
4350 | AI_COUNT: "aiReplyCount",
4351 | AI_DATE: "lastAiDate",
4352 | };
4353 |
4354 | function getToday() {
4355 | return new Date().toISOString().split("T")[0];
4356 | }
4357 |
4358 | function init() {
4359 | try {
4360 | const midnight = new Date();
4361 | midnight.setDate(midnight.getDate() + 1);
4362 | midnight.setHours(0, 0, 0, 0);
4363 | setTimeout(() => {
4364 | localStorage.removeItem(STORAGE.AI_COUNT);
4365 | localStorage.removeItem(STORAGE.AI_DATE);
4366 | localStorage.removeItem(STORAGE.LETTER);
4367 | }, midnight - Date.now());
4368 | UI.init();
4369 | document.body.style.position = "relative";
4370 | const today = getToday();
4371 | if (location.pathname.includes("/jobs")) {
4372 | if (localStorage.getItem(STORAGE.LETTER) !== today) {
4373 | letter.showLetterToUser();
4374 | localStorage.setItem(STORAGE.LETTER, today);
4375 | } else if (localStorage.getItem(STORAGE.GUIDE) !== "true") {
4376 | guide.showGuideToUser();
4377 | localStorage.setItem(STORAGE.GUIDE, "true");
4378 | Core.delay(800);
4379 | window.open(
4380 | "https://www.zhipin.com/web/geek/notify-set?ka=notify-set",
4381 | "_blank"
4382 | );
4383 | }
4384 | Core.log("欢迎使用海投助手,我将自动投递岗位!");
4385 | } else if (location.pathname.includes("/chat")) {
4386 | Core.log("欢迎使用海投助手,我将自动发送简历!");
4387 | } else if (location.pathname.includes("/notify-set")) {
4388 | Core.log("请将常用语换为自我介绍来引起HR的注意!");
4389 |
4390 | const targetSelector = "h3.normal.title";
4391 |
4392 | const observer = new MutationObserver((mutations, obs) => {
4393 | const targetElement = document.querySelector(targetSelector);
4394 | if (targetElement) {
4395 | targetElement.textContent =
4396 | "把常用语换为自我介绍,并设图片简历; 招呼语功能必须启用。";
4397 | obs.disconnect();
4398 | }
4399 | });
4400 |
4401 | observer.observe(document.body, {
4402 | childList: true,
4403 | subtree: true,
4404 | });
4405 | } else {
4406 | Core.log("当前页面暂不支持,请移步至职位页面!");
4407 | }
4408 | } catch (error) {
4409 | console.error("初始化失败:", error);
4410 | if (UI.notify) UI.notify("初始化失败", "error");
4411 | }
4412 | }
4413 |
4414 | window.addEventListener("load", init);
4415 | })();
4416 |
--------------------------------------------------------------------------------