diff --git a/third_party/operatophone/config.xml b/third_party/operatophone/config.xml
new file mode 100644
index 0000000..b53300d
--- /dev/null
+++ b/third_party/operatophone/config.xml
@@ -0,0 +1,27 @@
+
+
+ Opera to Phone
+ This extension adds a button to Opera that lets you seamlessly push links, maps, youtube videos, phone numbers and text to copy to the clipboard directly to your Android device. You also need to install the Chrome to Phone Android application on your phone. The application can be downloaded from Android Market (search for 'Chrome to Phone'). Requires a mobile phone running Android 2.2 ("Froyo") or later.
+ Rich Tibbett
+
+
+
+Copyright 2010 Opera Software ASA.
+
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+
+Portions of this work are modifications based on work created and shared
+by Google and used according to terms described in the Creative Commons 3.0
+Attribution License.
+
+
diff --git a/third_party/operatophone/constants.js b/third_party/operatophone/constants.js
new file mode 100644
index 0000000..e37f833
--- /dev/null
+++ b/third_party/operatophone/constants.js
@@ -0,0 +1,32 @@
+/*
+ * Portions of this page are modifications based on work created and shared
+ * by Google and used according to terms described in the Creative Commons 3.0
+ * Attribution License.
+ */
+
+var apiVersion = 5;
+var baseUrl = 'https://chrometophone.appspot.com';
+var sendUrl = baseUrl + '/send?ver=' + apiVersion;
+var signInUrl = baseUrl + '/signin?extret=' +
+encodeURIComponent('http://code.google.com/p/chrometophone/logo') + '?login';
+var signOutUrl = baseUrl + '/signout?extret=' +
+encodeURIComponent('http://code.google.com/p/chrometophone/logo') + '?logout';
+var registerUrl = baseUrl + '/register?ver=' + apiVersion;
+var apkUrl = 'http://code.google.com/p/chrometophone/wiki/AndroidApp';
+
+var ACTION_START_SEND = 'start_send_process';
+var ACTION_SEND_PAGE = 'send_to_phone';
+var ACTION_APK_REQUIRED = 'apk_required';
+var ACTION_REGISTER_USERJS = 'register_userjs';
+var ACTION_DEREGISTER_USERJS = 'deregister_userjs';
+var ACTION_CAPTURE_SELECTION = 'capture_selection';
+var ACTION_SELECTION_CAPTURED = 'selection_captured';
+
+var STATUS_SUCCESS = 'success';
+var STATUS_LOGIN_REQUIRED = 'login_required';
+var STATUS_DEVICE_NOT_REGISTERED = 'device_not_registered';
+var STATUS_HTTP_PAGES_ONLY = 'http_pages_only';
+var STATUS_GENERAL_ERROR = 'general_error';
+var STATUS_NO_TAB_ACCESS = 'no_tab_access';
+
+var BROWSER_CHANNEL_RETRY_INTERVAL_MS = 10000 * (1 + Math.random() - 0.5);
diff --git a/third_party/operatophone/help.html b/third_party/operatophone/help.html
new file mode 100644
index 0000000..b8b57d5
--- /dev/null
+++ b/third_party/operatophone/help.html
@@ -0,0 +1,46 @@
+
+
+ Opera to Phone
+
+
+
+Opera to Phone Extension - Help
+
+Welcome to Opera to Phone.
+
+
+ This extension adds a button to Opera that allows users to send links from their Opera desktop browser to their Android device using Android's Cloud to Device Messaging service.
+
+
+ You need to install the Chrome to Phone Android application on your
+ phone for this extension to work. The application can be downloaded from Android Market (search for 'Chrome to Phone'). Requires a mobile
+ phone running Android 2.2 ("Froyo") or later.
+
+
+Extension Features:
+
+
+ - Send links to browser.
+ - Google Maps links launch the Google Maps app.
+ - YouTube links launch the YouTube app.
+ - Selecting phone numbers in Web pages, launches the dialer with the number pre-populated.
+ - Selected text populates the Android clipboard (long-press on text boxes to get paste option).
+ - Right click on links and selections.
+
+
+Requirements
+
+
+ - Opera 11 (Alpha build 1024+)
+ - Android 2.2 ("Froyo") device
+ - Chrome to Phone application installed on Android device
+
+
+
+ *** This is an experimental port of the Chrome to Phone extension to Opera 11 but it has been tested and is working ***
+
+
+If you have any questions, comments or feedback, please email me at richt@opera.com.
+
+
+
\ No newline at end of file
diff --git a/third_party/operatophone/icon.png b/third_party/operatophone/icon.png
new file mode 100644
index 0000000..a7ac15e
Binary files /dev/null and b/third_party/operatophone/icon.png differ
diff --git a/third_party/operatophone/icon_64.png b/third_party/operatophone/icon_64.png
new file mode 100644
index 0000000..d6f08cd
Binary files /dev/null and b/third_party/operatophone/icon_64.png differ
diff --git a/third_party/operatophone/includes/operatophone.js b/third_party/operatophone/includes/operatophone.js
new file mode 100644
index 0000000..609f6d4
--- /dev/null
+++ b/third_party/operatophone/includes/operatophone.js
@@ -0,0 +1,64 @@
+// ==UserScript==
+// @include *
+// ==/UserScript==
+
+// obtain access to all tabs
+
+var ACTION_REGISTER_USERJS = 'register_userjs';
+var ACTION_DEREGISTER_USERJS = 'deregister_userjs';
+var ACTION_CAPTURE_SELECTION = 'capture_selection';
+var ACTION_SEND_PAGE = 'send_to_phone';
+
+function S4() {
+ return (((1+Math.random())*0x10000)|0).toString(16).substring(1);
+}
+function guid() {
+ return (S4()+S4()+"-"+S4()+"-"+S4()+"-"+S4()+"-"+S4()+S4()+S4());
+}
+
+if(!window.top.userJS_UUID) {
+ window.top.userJS_UUID = guid();
+
+ window.addEventListener('focus', function(){
+ opera.extension.postMessage({action: ACTION_REGISTER_USERJS, uuid: window.top.userJS_UUID});
+ }, false);
+
+ window.addEventListener('blur', function(){
+ opera.extension.postMessage({action: ACTION_DEREGISTER_USERJS, uuid: window.top.userJS_UUID});
+ }, false);
+
+ // register this tab as the active userjs onload
+ opera.extension.postMessage({action: ACTION_REGISTER_USERJS, uuid: window.top.userJS_UUID});
+}
+
+opera.extension.addEventListener('message', function(request) {
+
+ //opera.postError('Callback received at UserJS: ' + request.data.action);
+
+ if(request.data.action==ACTION_CAPTURE_SELECTION
+ && request.data.uuid==window.top.userJS_UUID) {
+
+ var currentUrl = document.location.href;
+
+ var pageInfo = {
+ action: ACTION_SEND_PAGE,
+ data: {
+ link: encodeURIComponent(currentUrl),
+ title: encodeURIComponent(document.title),
+ selection: encodeURIComponent(window.getSelection())
+ }
+ };
+
+ // URL overrides
+ if (currentUrl.match(/^http[s]?:\/\/maps\.google\./) ||
+ currentUrl.match(/^http[s]?:\/\/www\.google\.[a-z]{2,3}(\.[a-z]{2})\/maps/)) {
+ var link = document.getElementById('link');
+ if (link && link.href)
+ pageInfo.data.link = encodeURIComponent(link.href);
+ }
+
+ opera.extension.postMessage(pageInfo);
+ }
+}, false);
+
+//opera.postError("UserJS loaded: " + window.location.href + " / " + window.top.userJS_UUID);
\ No newline at end of file
diff --git a/third_party/operatophone/index.html b/third_party/operatophone/index.html
new file mode 100644
index 0000000..6db3e47
--- /dev/null
+++ b/third_party/operatophone/index.html
@@ -0,0 +1,108 @@
+
+
+
+
+
+
+
+
+
+
diff --git a/third_party/operatophone/popup.html b/third_party/operatophone/popup.html
new file mode 100644
index 0000000..324b990
--- /dev/null
+++ b/third_party/operatophone/popup.html
@@ -0,0 +1,114 @@
+
+
+
+
+
+
+
+
+
+
+  |
+
+
+ |
+
+ |
+
+
+
+
\ No newline at end of file
diff --git a/third_party/operatophone/send_logic.js b/third_party/operatophone/send_logic.js
new file mode 100644
index 0000000..b9c570e
--- /dev/null
+++ b/third_party/operatophone/send_logic.js
@@ -0,0 +1,37 @@
+/*
+ * Portions of this page are modifications based on work created and shared
+ * by Google and used according to terms described in the Creative Commons 3.0
+ * Attribution License.
+ */
+
+var channel;
+var socket;
+var req = new XMLHttpRequest();
+
+function sendToPhone(title, url, sel, msgType, listener) {
+ req.open('POST', sendUrl, true);
+ req.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
+ req.setRequestHeader('X-Same-Domain', 'true'); // XSRF protector
+
+ req.onreadystatechange = function() {
+ if (this.readyState == 4) {
+ if (req.status == 200) {
+ var body = req.responseText;
+ if (body.indexOf('OK') == 0) {
+ listener(STATUS_SUCCESS);
+ } else if (body.indexOf('LOGIN_REQUIRED') == 0) {
+ listener(STATUS_LOGIN_REQUIRED);
+ } else if (body.indexOf('DEVICE_NOT_REGISTERED') == 0) {
+ listener(STATUS_DEVICE_NOT_REGISTERED);
+ }
+ } else {
+ listener(STATUS_GENERAL_ERROR);
+ }
+ }
+ };
+
+ // title, url and sel have already been encoded...
+ var data = 'title=' + title + '&url=' + url +
+ '&sel=' + sel + '&type=' + encodeURIComponent(msgType);
+ req.send(data);
+}