【问题标题】:UIWebView Content OffsetUIWebView 内容偏移
【发布时间】:2014-03-11 08:14:30
【问题描述】:

我想在我的应用程序中的 UIWebView 中显示一个 google.maps url,但该页面出现的位置与我想要的不同。我在这里尝试了许多问题的所有内容,例如设置 webview.scrollview 或 contentInset 或 scrollsToTop 的 contentOffset ,甚至使用 javascript 命令,但它们都不起作用。所以这就是问题所在:

这是我想要的预期结果:

我希望我的网页出现在顶部而不是中间。

网址url

【问题讨论】:

  • 如何生成/获取 URL?也许它包括跳到锚点?
  • 感谢@Toastor 的回复。当我添加一些 POIS 时,该网址已从谷歌获取。我编辑了我的问题并添加了网址。我没有格式化网址。

标签: ios objective-c uiwebview


【解决方案1】:

这与内容偏移等无关 - 它是页面本身在完成加载后立即向下滚动。在 Mobile Safari 中加载 URL 时,您将获得完全相同的行为,甚至可以观察到滚动动画。

不幸的是,除了在将其加载到 webview 之前从服务器提供的 html 中提取滚动代码之外,您无法采取任何措施来阻止它。这将是乏味的,无论如何您都不应该这样做,因为一旦 google 对该页面的内部工作进行更改,这可能会破坏您的应用程序。

我现在能想到的唯一解决方案是在页面向下滚动后以编程方式将页面滚动回顶部。我已经用您提供的网址进行了尝试,它确实有效。为此,请在 webview 委托中实现 webViewDidFinishLoad:,如下所示:

-(void)webViewDidFinishLoad:(UIWebView *)webView {

   NSTimer *scrollTimer = [NSTimer scheduledTimerWithTimeInterval:2 target:self selector:@selector(scrollBackToTop) userInfo:nil repeats:NO]; // Better make the timer an ivar

}

并实现如下方法:

-(void)scrollBackToTop {

   NSString* javascript = [NSString stringWithFormat:@"window.scrollTo(0, 0);"];
   [theWebView stringByEvaluatingJavaScriptFromString:javascript];

}

这当然意味着您的 webview 将首先明显地向下滚动,然后才跳回顶部,这相当难看。因此,您可能希望将 webview 隐藏在包含活动指示器等的不透明视图后面,直到 webview 加载并完成所有滚动操作...

请注意,虽然这种可能性较小且致命性较小,但它也可能会中断。当我尝试我的解决方案时,2 秒的延迟就足够了。如果谷歌在未来放慢动画速度,2 秒可能还不够,你的 scrollBackToTop 方法会提前触发。由于java脚本不会取消正在进行的滚动,所以它根本不会滚动回顶部。

编辑:

也许我有更好的东西给你...

在您的 webViewDidFinishLoad: 方法中执行以下操作:

NSString* javascript = [NSString stringWithFormat:@"document.getElementById('panel').style.position='fixed'; document.getElementById('panel').style.top='50px';"];
[webView stringByEvaluatingJavaScriptFromString:javascript];

这将完全抑制滚动动画。但这是有代价的:如果用户现在手动滚动 webview,表单字段保持固定位置,而页面的其余部分正常滚动。

所以你需要通过这样做来撤消黑客攻击:

NSString* javascript = [NSString stringWithFormat:@"document.getElementById('panel').style.position='absolute'; document.getElementById('panel').style.top='0px';"];
[theWebView stringByEvaluatingJavaScriptFromString:javascript];

您需要在滚动脚本完成后再次延迟执行第二步,否则页面将完全滚动。对我来说,延迟 1.2 秒就可以了。

您可能希望通过在计时器触发之前禁用 webviews 滚动视图上的滚动来防止用户在这 1.2 秒内滚动。

因此仍有改进的余地,但与隐藏 webview 直到它来回滚动相比,这种方法可能会让您的应用感觉更灵敏...

【讨论】:

    猜你喜欢
    • 2011-04-01
    • 2011-06-07
    • 2010-12-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-04
    • 2014-07-03
    相关资源
    最近更新 更多