javascript 在页面重新加载时滚动到包含iframe的第二部分的问题

mpbci0fu  于 2023-06-04  发布在  Java
关注(0)|答案(2)|浏览(142)

我有一个网站,我使用第三方公司的iframe。iframe被放置在ID为“iframe”的div中。我面临的问题是,当用户单击iframe中的任何按钮时,它会重新加载整个页面,滚动位置会重置为顶部。结果,用户需要再次向下滚动以查看更新的内容,这是不理想的。此外,用户甚至不会怀疑发生了什么事情,因为iframe被放置在网站的第二部分。
我尝试在加载完成后使用JavaScript滚动到包含iframe的第二部分。然而,到目前为止,我还没有成功。
我不确定这是不是正确的方法。我已经尝试使用此代码(它是由其他人提供的)。但在重新加载iFrame后,新位置被设置为“0”:

Saved scroll position: 0
    Iframe reloaded

可能代码必须只在iFrame中点击时触发,链接在开始时有一些 * 公共模式 *。
下面是我目前使用的代码:

window.onload = function() {
  var iframeContainer = document.getElementById("iframe");
  var iframe = iframeContainer.querySelector("iframe");
  var iframeSrc = iframe.getAttribute("src");

  console.log("Page loaded");

  // Check if there is a stored scroll position in the URL and restore it
  var scrollPosition = getScrollPositionFromUrl();
  if (scrollPosition) {
    window.scrollTo(0, scrollPosition);
    console.log("Restored scroll position:", scrollPosition);
  }

  // Save the scroll position in the URL when the user scrolls
  window.addEventListener("scroll", function() {
    var scrollPosition = window.pageYOffset || document.documentElement.scrollTop;
    setScrollPositionToUrl(scrollPosition);
    console.log("Saved scroll position:", scrollPosition);
  });

  // Modify the iframe code to remove scroll position from the URL on reload
  iframe.addEventListener("load", function() {
    removeScrollPositionFromUrl();
    console.log("Iframe reloaded");
  });

  // Function to retrieve scroll position from URL
  function getScrollPositionFromUrl() {
    var hash = window.location.hash;
    if (hash) {
      var scrollPosition = parseInt(hash.substring(1));
      if (!isNaN(scrollPosition)) {
        return scrollPosition;
      }
    }
    return null;
  }

  // Function to set scroll position to URL
  function setScrollPositionToUrl(scrollPosition) {
    var hash = "#" + scrollPosition;
    history.replaceState(null, null, hash);
  }

  // Function to remove scroll position from URL
  function removeScrollPositionFromUrl() {
    history.replaceState(null, null, window.location.pathname);
  }
};

我将感谢任何关于如何解决这个问题的帮助。如何确保页面在加载完成后自动滚动到包含iframe的第二个部分?提前感谢您的帮助!

更新

我简化了方法:尝试检查URL是否包含常见模式,然后相应地操作滚动位置(使用散列链接)。但是,这种方法并不一致,并且在页面重新加载后,滚动位置不能正确恢复。
重要的是,我发现当点击iframe中的链接时,主页面不会完全重新加载。因此,主页的网址是更新后的新地址iFrame重新加载和滚动是带我到顶部。因此,当URL更改时,我实现的代码没有机会执行。
这里我尝试了:

window.addEventListener("load", function() {
  var iframeContainer = document.getElementById("iframe");
  var iframe = iframeContainer.querySelector("iframe");
  var commonUrlPattern = "/?step=index/step3"; // Update the common URL pattern as needed

  console.log("Page loaded");

  // Check if the URL contains the common pattern and the iframe has loaded
  if (window.location.href.includes(commonUrlPattern)) {
    console.log("Common URL pattern found");
    scrollToSection();
  }

  // Function to scroll to the custom section
  function scrollToSection() {
    // Replace 'section-id' with the actual ID of the section you want to scroll to
    var sectionId = "section-id";
    var sectionElement = document.getElementById(sectionId);
    if (sectionElement) {
      sectionElement.scrollIntoView({ behavior: "smooth" });
    }
  }

  // Listen for iframe load event to track URL changes within the iframe
  iframe.addEventListener("load", function() {
    console.log("Iframe loaded");
    var iframeUrl = iframe.contentWindow.location.href;
    if (iframeUrl.includes(commonUrlPattern)) {
      console.log("Common URL pattern found within iframe");
      scrollToSection();
    }
  });
});

@Mark Schultheiss提供了建议,基于此代码工作:

<script>
  // Define the common URL patterns to match against
  var commonUrlPatterns = [
    "/?step=index/step3",
    "/?step=index/step2/show"
    // Add more patterns as needed
  ];

  // Function to get the current URL
  function getCurrentURL() {
    return window.location.href;
  }

  // Store the initial URL
  var initialUrl = getCurrentURL();

  // Store the current URL
  var currentUrl = initialUrl;

  // Function to check for URL changes
  function checkURLChange() {
    // Get the previous URL
    var previousUrl = currentUrl;

    // Get the current URL
    currentUrl = getCurrentURL();

    if (currentUrl !== previousUrl) {
      // Check if the URL matches any of the common patterns
      var matchedPattern = commonUrlPatterns.find(function (pattern) {
        return currentUrl.includes(pattern);
      });

      if (matchedPattern) {
        // Perform the desired action based on the matched pattern
                  
            scrollToSection("#iframe");            
        
      }
    }
  }

  // Function to scroll to a specific section
  function scrollToSection(targetSelector) {
    var targetElement = document.querySelector(targetSelector);
    if (targetElement) {
      targetElement.scrollIntoView({ behavior: "smooth" });
    }
  }

  // Check if the initial URL matches any of the common patterns
  var matchedInitialPattern = commonUrlPatterns.find(function (pattern) {
    return initialUrl.includes(pattern);
  });

  if (matchedInitialPattern) {
    // Perform the desired action based on the matched pattern
         
        scrollToSection("#iframe");     
    
  }

  // Periodically check for URL changes
  setInterval(checkURLChange, 1000); // Adjust the interval as needed (in milliseconds)
</script>
waxmsbnn

waxmsbnn1#

现代的方法是创建一个自定义事件,然后根据需要触发它。
在这里,我设置了hashchange事件处理程序来执行此操作(在此代码段中没有触发)
我还创建了一个“测试”,在这里将其作为一个片段触发,以便仅查看此示例的滚动效果。
这有点做作,但我认为你可以从这里开始。
参考:https://developer.mozilla.org/en-US/docs/Web/Events/Creating_and_triggering_events散列更改参考:https://developer.mozilla.org/en-US/docs/Web/API/Window/hashchange_event

const attachTo = '.bigger-is-me';//could be any element
const targetEventElement = document.querySelector(attachTo);
targetEventElement.dataset.scrollTarget = "#targetId";
targetEventElement.dataset.pattern = "/?step=index/step3";

// just for this example here!
const testThisExample = "https://stacksnippets.net/js"
targetEventElement.dataset.pattern = testThisExample

//so we can see this in the event handler we pass it
const details = {
  pattern: targetEventElement.dataset.pattern,
  seeme: targetEventElement.dataset.scrollTarget
};

//create custom event with our details from above
const customEventScroll = new CustomEvent("scrollToSomething", {
  detail: details
});

function scrollToSection(targetElement) {
  targetElement.scrollIntoView({
    behavior: "smooth"
  });
}

function customEventHandler(ev) {
  //  console.log(`The pattern is: ${ev.detail.pattern} for ${ev.detail.seeme}`);
  const scrollTarget = document.querySelector(ev.detail.seeme);
  scrollToSection(scrollTarget);
}
// Listen for the custom event.
targetEventElement.addEventListener("scrollToSomething", customEventHandler, false);

//listen for the hash change; and dispatch event when it happens
window.addEventListener('hashchange', function() {
  document.querySelector("body").dispatchEvent(customEventScroll);
});
//just here in case page does not have pattern?
// THIS example test does not really use this.
function checkURLMatch(pattern) {
  const currentUrl = window.location.href;
  // Check if the URL matches the common pattern
  const isCommonUrl = currentUrl.includes(pattern);
  if (isCommonUrl) {
    document.querySelector(attachTo)
      .dispatchEvent(customEventScroll);
  }
}
// dispatch the event on page load here JUST FOR THIS TEST
checkURLMatch(targetEventElement.dataset.pattern);
body {
  font-size: 16px;
  margin: 0;
  padding: 0;
}

.bigger-is-me {
  height: 100vh;
  border: solid 1px #FF0000;
  margin-bottom: 1em;
}

.fun-guy {
  margin-bottom: 5em;
}
<div class="bigger-is-me"> I just create some space to test</div>
<div id="targetId" class="fun-guy">I am the target, could be the iframe</div>
68de4m5k

68de4m5k2#

我用过这段代码,看起来很有效,但如果有人能建议改进代码,我会很感激:

// Define the common URL pattern to match against
  var commonUrlPattern = "/?step=index/step3";

  // Function to get the current URL
  function getCurrentURL() {
    return window.location.href;
  }

  // Store the initial URL
  var initialUrl = getCurrentURL();

  // Store the current URL
  var currentUrl = initialUrl;

  // Function to check for URL changes
  function checkURLChange() {
    // Get the previous URL
    var previousUrl = currentUrl;

    // Get the current URL
    currentUrl = getCurrentURL();

    if (currentUrl !== previousUrl) {
      // alert("URL changed:\nPrevious URL: " + previousUrl + "\nCurrent URL: " + currentUrl);

      // Check if the URL matches the common pattern
      var isCommonUrl = currentUrl.includes(commonUrlPattern);

      if (isCommonUrl) {
        // alert("Common URL pattern found");
        // Perform the desired action or function here
        // For example, scroll to a specific section
        scrollToSection();
      } else {
        // alert("Common URL pattern not found");
      }
    }
  }

  // Function to scroll to a specific section
  function scrollToSection() {
    // Your code to scroll to the desired section goes here
    // For example:
    var targetElement = document.getElementById("iframe");
    if (targetElement) {
      targetElement.scrollIntoView({ behavior: "smooth" });
    }
  }

  // Check if the initial URL matches the common pattern
  var isInitialUrlCommon = initialUrl.includes(commonUrlPattern);
  if (isInitialUrlCommon) {
    // alert("Common URL pattern found initially");
    // Perform the desired action or function here
    // For example, scroll to a specific section
    scrollToSection();
  } else {
    // alert("Common URL pattern not found initially");
  }

  // Periodically check for URL changes
  setInterval(checkURLChange, 1000); // Adjust the interval as needed (in milliseconds)

相关问题