blob: bc8452305f6c093ba8caca31ba464c049f2eb483 [file] [log] [blame]
Michael Kolb14612442011-06-24 13:06:29 -07001/*
2 * Copyright (C) 2011 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16package com.android.browser;
17
18import android.content.Context;
19import android.os.Handler;
20import android.os.Looper;
Michael Kolb14612442011-06-24 13:06:29 -070021import android.util.Log;
Mathew Inwoode1dbb952011-07-08 17:27:38 +010022import android.webkit.WebView;
Michael Kolb14612442011-06-24 13:06:29 -070023
24import java.util.HashMap;
25import java.util.Map;
26
27/**
28 * Singleton class for handling preload requests.
29 */
30public class Preloader {
31
32 private final static String LOGTAG = "browser.preloader";
Mathew Inwood29721c22011-06-29 17:55:24 +010033 private final static boolean LOGD_ENABLED = com.android.browser.Browser.LOGD_ENABLED;
Michael Kolb14612442011-06-24 13:06:29 -070034
35 private static final int PRERENDER_TIMEOUT_MILLIS = 30 * 1000; // 30s
36
37 private static Preloader sInstance;
38
39 private final Context mContext;
40 private final Handler mHandler;
41 private final BrowserWebViewFactory mFactory;
42 private final HashMap<String, PreloaderSession> mSessions;
43
44 public static void initialize(Context context) {
45 sInstance = new Preloader(context);
46 }
47
48 public static Preloader getInstance() {
49 return sInstance;
50 }
51
52 private Preloader(Context context) {
53 mContext = context;
54 mHandler = new Handler(Looper.getMainLooper());
55 mSessions = new HashMap<String, PreloaderSession>();
56 mFactory = new BrowserWebViewFactory(context);
57
58 }
59
60 private PreloaderSession getSession(String id) {
61 PreloaderSession s = mSessions.get(id);
62 if (s == null) {
63 if (LOGD_ENABLED) Log.d(LOGTAG, "Create new preload session " + id);
64 s = new PreloaderSession(id);
65 mSessions.put(id, s);
Mathew Inwoode1dbb952011-07-08 17:27:38 +010066 WebViewTimersControl.getInstance().onPrerenderStart(s.getWebView());
Michael Kolb14612442011-06-24 13:06:29 -070067 }
68 return s;
69 }
70
71 private PreloaderSession takeSession(String id) {
72 PreloaderSession s = mSessions.remove(id);
73 if (s != null) {
74 s.cancelTimeout();
75 }
Mathew Inwoode1dbb952011-07-08 17:27:38 +010076 if (mSessions.size() == 0) {
77 WebViewTimersControl.getInstance().onPrerenderDone(s == null ? null : s.getWebView());
78 }
Michael Kolb14612442011-06-24 13:06:29 -070079 return s;
80 }
81
Mathew Inwood29721c22011-06-29 17:55:24 +010082 public void handlePreloadRequest(String id, String url, Map<String, String> headers,
83 String searchBoxQuery) {
Michael Kolb14612442011-06-24 13:06:29 -070084 PreloaderSession s = getSession(id);
85 s.touch(); // reset timer
Mathew Inwood29721c22011-06-29 17:55:24 +010086 PreloadedTabControl tab = s.getTabControl();
87 if (searchBoxQuery != null) {
88 tab.loadUrlIfChanged(url, headers);
89 tab.setQuery(searchBoxQuery);
90 } else {
91 tab.loadUrl(url, headers);
92 }
Michael Kolb14612442011-06-24 13:06:29 -070093 }
94
95 public void discardPreload(String id) {
96 PreloaderSession s = takeSession(id);
97 if (s != null) {
98 if (LOGD_ENABLED) Log.d(LOGTAG, "Discard preload session " + id);
Mathew Inwood29721c22011-06-29 17:55:24 +010099 PreloadedTabControl t = s.getTabControl();
Michael Kolb14612442011-06-24 13:06:29 -0700100 t.destroy();
Mathew Inwood29721c22011-06-29 17:55:24 +0100101 } else {
102 if (LOGD_ENABLED) Log.d(LOGTAG, "Ignored discard request " + id);
Michael Kolb14612442011-06-24 13:06:29 -0700103 }
104 }
105
106 /**
107 * Return a preloaded tab, and remove it from the preloader. This is used when the
108 * view is about to be displayed.
109 */
Mathew Inwood29721c22011-06-29 17:55:24 +0100110 public PreloadedTabControl getPreloadedTab(String id) {
Michael Kolb14612442011-06-24 13:06:29 -0700111 PreloaderSession s = takeSession(id);
112 if (LOGD_ENABLED) Log.d(LOGTAG, "Showing preload session " + id + "=" + s);
Mathew Inwood29721c22011-06-29 17:55:24 +0100113 return s == null ? null : s.getTabControl();
Michael Kolb14612442011-06-24 13:06:29 -0700114 }
115
116 private class PreloaderSession {
117 private final String mId;
Mathew Inwood29721c22011-06-29 17:55:24 +0100118 private final PreloadedTabControl mTabControl;
Michael Kolb14612442011-06-24 13:06:29 -0700119
120 private final Runnable mTimeoutTask = new Runnable(){
121 @Override
122 public void run() {
123 if (LOGD_ENABLED) Log.d(LOGTAG, "Preload session timeout " + mId);
124 discardPreload(mId);
125 }};
126
127 public PreloaderSession(String id) {
128 mId = id;
Mathew Inwood29721c22011-06-29 17:55:24 +0100129 mTabControl = new PreloadedTabControl(
130 new Tab(new PreloadController(mContext), mFactory.createWebView(false)));
Michael Kolb14612442011-06-24 13:06:29 -0700131 touch();
132 }
133
134 public void cancelTimeout() {
135 mHandler.removeCallbacks(mTimeoutTask);
136 }
137
138 public void touch() {
139 cancelTimeout();
140 mHandler.postDelayed(mTimeoutTask, PRERENDER_TIMEOUT_MILLIS);
141 }
142
Mathew Inwood29721c22011-06-29 17:55:24 +0100143 public PreloadedTabControl getTabControl() {
144 return mTabControl;
Michael Kolb14612442011-06-24 13:06:29 -0700145 }
146
Mathew Inwoode1dbb952011-07-08 17:27:38 +0100147 public WebView getWebView() {
148 Tab t = mTabControl.getTab();
149 return t == null? null : t.getWebView();
150 }
151
Michael Kolb14612442011-06-24 13:06:29 -0700152 }
153
154}