PhoneGap: Masaüstü tarayıcıda çalışıp çalışmadığını algıla


118

PhoneGap: Build for a mobile version kullanan bir web uygulaması geliştiriyorum ve 'masaüstü' ve mobil versiyonlar için tek bir kod tabanına sahip olmak istiyorum. PhoneGap aramalarının çalışıp çalışmayacağını tespit edebilmek istiyorum (yani, kullanıcı PhoneGap'ı destekleyecek bir mobil cihaz kullanıyor mu).

Araştırdım ve bunu yapmanın basit bir yolu olmadığına inanamıyorum. Birçok kişi önerilerde bulundu;

PhoneGap Javascript dosyasını uygulamanın masaüstü sürümünden kaldırmadığınız sürece hiçbiri işe yaramaz, bu da benim bir kod tabanına sahip olma hedefimi bozar.

Şimdiye kadar bulduğum tek çözüm tarayıcı / kullanıcı aracısı koklamaktı, ancak bu en azını söylemek zor değil. Daha iyi çözümler hoş geldiniz!

DÜZENLEME: Biraz daha iyi bir çözüm, küçük bir zaman aşımından sonra bir PhoneGap işlevini çağırmayı denemektir - eğer işe yaramazsa, kullanıcının bir masaüstü web tarayıcısında olduğunu varsayın.


Build'i kullandığınız için, @ bt'nin aşağıdaki yanıtına bakın: stackoverflow.com/a/18478002/241244 . Kabul edilen ve en çok oylanan cevaplardan daha iyi gibi görünüyor.

% 100 etkili olduğu için açık derleme zamanı yapılandırması lehine çalışma zamanı algılamasından kaçınıyorum. Index.jade şablonuma {isPhonegap: true} gibi bir yerel var aktarırım, ardından şablona koşullu olarak phonegap.js komut dosyasını ekleyebilir ve istediğim tüm telefon aralığına özgü başlatmayı gerçekleştirebilirim.
Jesse Hattabaugh

Yanıtlar:


115

Bu kodu kullanıyorum:

if (navigator.userAgent.match(/(iPhone|iPod|iPad|Android|BlackBerry|IEMobile)/)) {
  document.addEventListener("deviceready", onDeviceReady, false);
} else {
  onDeviceReady(); //this is the browser
}

GÜNCELLEME

Telefon aralığının bir tarayıcıda çalışıp çalışmadığını belirlemenin başka birçok yolu vardır, işte başka bir harika seçenek:

var app = document.URL.indexOf( 'http://' ) === -1 && document.URL.indexOf( 'https://' ) === -1;
if ( app ) {
    // PhoneGap application
} else {
    // Web page
}  

burada görüldüğü gibi: Bir mobil tarayıcı veya bir PhoneGap uygulaması arasında algılama


Bunun için teşekkürler - başkalarının ne önerdiğini görmek için uzun süre bekledikten sonra, bu en iyi çözüm gibi görünüyor. Şerefe.
aaronsnoswell

35
Bu doğru değil, çünkü aynı sayfayı Aygıtın gözatmasında açarsam, onDeviceReady () asla aramaz. Ayrıca, tarayıcıdaki UserAgent'ı değiştirirsem (hata ayıklama amacıyla), onDeviceReady () hiçbir zaman ikisini de çağırmaz.
Slavik Meltser

3
Ne söylediğinizden emin değilsiniz - ancak bunun telefon tarayıcısını kullanırken sorunlara neden olacağını ima ediyorsunuz gibi görünüyor ... Bu, telefonlarınızda değil masaüstü tarayıcınızda test etmek için bir çözümdür.
sirmdawg

7
Bu, uygulamayı cihaz tarayıcısında açtığınızda yardımcı olmaz. Daha iyi çözüm: window.cordova'yı kontrol edin. İPhone Simulator'da (tarayıcı) veya bir Android cihazda (tarayıcı) yapılan testler de PhoneGap'i algılamalıdır. Ben böyle geliştiriyorum. Ancak işleri halletmek için birçok olasılık var. ;-) Çözümünüzü göndermek için teşekkürler!
Mario

Kafam karıştı, peki ya Windows Phone gibi diğer platformlar? Bu normal ifadeyle eşleşen bir userAgent var mı? Hızlı bir Google araması şunu ima eder: madskristensen.net/post/Windows-Phone-7-user-agents.aspx
mooreds

49

Birkaç gün önce bunun hakkında bir yazı yazdım . Bu bulabileceğiniz en iyi çözümdür (PhoneGap bir şeyi yayınlayana kadar, belki de yayımlamaz), kısa, basit ve mükemmel (mümkün olan her şekilde ve platformda kontrol ettim).

Bu işlev, işi vakaların% 98'inde yapacak.

/**
 * Determine whether the file loaded from PhoneGap or not
 */
function isPhoneGap() {
    return (window.cordova || window.PhoneGap || window.phonegap) 
    && /^file:\/{3}[^\/]/i.test(window.location.href) 
    && /ios|iphone|ipod|ipad|android/i.test(navigator.userAgent);
}

if ( isPhoneGap() ) {
    alert("Running on PhoneGap!");
} else {
    alert("Not running on PhoneGap!");
}

Vakaların diğer% 2'sini tamamlamak için şu adımları izleyin (yerel kodda küçük bir değişiklik içerir):

__Phonegap_index.html adlı , şu kaynakla bir dosya oluşturun :

<!-- __phonegap_index.html -->
<script type="text/javascript">
    function isPhoneGap() {
        //the function's content is as described above
    }

    //ensure the 98% that this file is called from PhoneGap.
    //in case somebody accessed this file directly from the browser.
    if ( isPhoneGap() )
        localStorage.setItem("isPhoneGap","1");

    //and redirect to the main site file.
    window.location = "index.html";
</script>

Şimdi, yerli üzerinde basitçe gelen başlangıç sayfasını değiştirmek index.html için __phonegap_index.html tüm PhoneGap platformlarında. Diyelim ki proje adım örnek olsun , değiştirmeniz gereken dosyalar (PhoneGap sürüm 2.2.0'da olduğu gibi):

  • iOS -CordovaLibApp/AppDelegate.m
  • Android -src/org/apache/cordova/example/cordovaExample.java
  • Windows 8 -example/package.appxmanifest
  • BlackBerry -www/config.xml
  • WebOS -framework/appinfo.json
  • Bada - src/WebForm.cpp(satır 56)
  • Window Phone 7 - Nerede olduğu hakkında hiçbir fikriniz yok (biri hala bu platformda geliştiriyor mu ?!)

Son olarak, PhoneGap üzerinde çalışıyor olsa da olmasa da sitenizin herhangi bir yerinde kullanabilirsiniz:

if ( localStorage.getItem("isPhoneGap") ) {
    alert("Running on PhoneGap!");
} else {
    alert("Not running on PhoneGap!");
}

Umarım yardımcı olur. :-)


4
Bu cevabı en iyisi olarak buldum!
blong824

3
evet işe yarıyor ama bazen kodun sonraki bölümü doğru /^file:\/{3}[^\/]/i.test(window.location.href)değil ama PhoneGap kullanıyoruz, örneğin başka bir sayfadan index.html'yi yüklerken, config.xml'de buna benzer bir şey<content src="http://10.100.1.147/" />
vudduu

3
Bu (cordova || PhoneGap || phonegap) değişkenlerden herhangi biri tanımlanmamışsa, ifade bir ReferenceError hatası atar. İle test etmelisin typeof cordova !== undefined, değil mi?
rojobuffalo

1
@rblakeley haklısın. İlk satırı şu şekilde değiştirdim:return ( typeof cordova !== undefined || typeof PhoneGap !== undefined || typeof phonegap !== undefined )
ethanpil

1
@rojobuffalo: Görünüşe göre cevap değiştirilmiş ve tekrar beklendiği gibi çalışıyor ( yani önek ReferenceErrornedeniyle artık bir atamıyor window). Buna işaret edeceğimi düşündüm, çünkü bu aslında yorum zincirini modası geçmiş (ve dolayısıyla yanlış) yapıyor.
Priidu Neemre

27

Bir süre önce yanıtlandığını biliyorum ama "PhoneGap.available" artık mevcut değil. Kullanmalısın:

if (window.PhoneGap) {
  //do stuff
}

veya 1.7'den beri tercih edin:

if (window.cordova) {
  //do stuff
}

DÜZENLEME 2019: Yorumlarda belirtildiği gibi, bu yalnızca cordova lib'yi masaüstü tarayıcı yapınıza dahil etmezseniz çalışır. Ve elbette, hedeflediğiniz her cihaz için yalnızca katı minimum javascript / html / css dosyalarını dahil etmek iyi bir uygulamadır


18
Bu doğru değildir, çünkü window.PhoneGap veya window.cordova, tarayıcıya yüklenmiş olsa bile cordova-xxxjs komut dosyasını eklerseniz her durumda tanımlanacaktır.
Slavik Meltser

Bana bir örnek yardımcı olabilir misiniz? İndex.html'yi basitçe yüklemek için yaptığım şey, yerel sunucumdaki www klasörü altındaki tüm dosyaları yükledim, index.html'yi yüklüyorum ama cihaz hazır kovulmadı.
Nassif

5
Bu şimdi doğru cevap gibi görünüyor (en azından Cordova 3.4 ile). Diğer tüm yöntemler, cordova.js artık basit bir <script type = "text / javascript" src = "cordova.js"> </script> ile uygulamaya enjekte edildiği için zaman kaybıdır. Gerçekte gerçek dosyayı göstermezsiniz, bu yüzden bir tarayıcıda çalışırken yüklenmez. Yalnızca bir mobil cihaz üzerinde çalışan bir Cordova yapısında var.
Michael Oryl

PhoneGap Build kullanıyorsanız bu özellikle işe yarayacak gibi görünüyor.

4
@SlavikMe cordova betiğini cordova olmayan yapılara dahil etmeyin.
Jackson

21

Bir cordova / phonegap uygulamasında olup olmadığımızı anlamanın bulduğumuz en güvenilir yolu, bu AppendUserAgent yapılandırmasını kullanarak cordova uygulamasının kullanıcı aracısını değiştirmektir .

Ek olarak config.xml:

<preference name="AppendUserAgent" value="Cordova" />

Sonra ara:

var isCordova = navigator.userAgent.match(/Cordova/i))

Neden?

  1. window.cordovave document.addEventListener('deviceready', function(){});yarış koşullarına tabidir
  2. navigator.standalone<content src="index.html" />bir web sitesi olduğunda çalışmıyor (Örn: <content src="https://www.example.com/index.html" />veya cordova-eklenti-uzaktan enjeksiyon )
  3. Gerçek bir tarayıcı olup olmadığını tahmin etmek için kullanıcı aracılarını beyaz listeye almaya çalışmak çok karmaşıktır. Android tarayıcıları genellikle özel web görünümleridir.

2
Ve hatta uygulama sürümünü oraya ekleyebiliriz! (ideal olarak bazı otomatik sürüm çarpma mantığıyla) ex; Cordova AppName/v0.0.1<3 Bu şekilde, bunu bir şekilde izleme için bile kullanabilirsiniz (ancak herkesin kullanıcı
aracısını

Bu en kusursuz yöntem gibi görünüyor. İkinci koşucu, belge URL'sinde http: // veya https: // yokluğunu test ediyor gibi görünüyor, ancak bunun işe yaramayacağı olası senaryoları öngörebilirim.
JD Smith

14

Bunun en basit olduğunu düşünüyorum: var isPhoneGap = (location.protocol == "file:")

EDIT İşe yaramayan bazı insanlar için. O zaman deneyebilirsin (test etmedin)

var isPhoneGap = ! /^http/.test(location.protocol);

1
PhoneGap'in cihazdaki tüm dosyalar için dahili bir sunucu çalıştırdığını düşündüm.
aaronsnoswell

Bunu sevdim. Localhost üzerinde geliştirme yaparken, bu en iyi çözümdür. (Çok denedikten sonra, umarım bu tüm senaryolarda işe yarar.) Thx!
Mario

1
Uzak bir dosyayı test ederken bu dalgalanma öykünücüsünde çalışmıyor
Jesse Hattabaugh

Ayrıca WP8'de çalışmaz, protokol "x-wmapp0:" şeklindedir. Gelecekte başka hangi "protokollerin" kullanılacağını kesin olarak bilemiyorum.
Adrian

Ayrıca deneyebilirsinizvar isPhoneGap = ! /^http/.test(document.location.protocol)
Yuval

8

Bu benim için çalışıyor (1.7.0'da çalışıyor)

if (window.device) {
  // Running on PhoneGap
}

Masaüstü Chrome ve Safari'de test edilmiştir.


3
Bu, 'cihaz hazırlığı' olayına bağlanmakla neredeyse aynıdır. Window.device tanımlanmamışsa, phonegap / cordova'nın yüklenmesinin yavaş olup olmadığını veya olayın asla ateşlenmeyeceğini söyleyemezsiniz.
Wytze

8
window.device, "cihaz hazırlığı" olayı tetiklenmeden önce tanımlanmaz.
Slavik Meltser

2
Ve dua edin ki, başka hiçbir programcı "cihaz" adında yeni bir küresel değişken tanımlama konusunda mutlu bir fikre sahip olmasın.
Bay Smith

7

Orijinal poster gibi, phonegap oluşturma hizmetini kullanıyorum. İki gün ve yaklaşık 50 test derlemesinden sonra, benim için harika çalışan zarif bir çözüm buldum.

Mobil tarayıcılarda test etmek ve çalıştırmak istediğim için UA koklamayı kullanamadım. Başlangıçta, Cobberboy'un oldukça işlevsel tekniğine karar vermiştim. Bu benim için işe yaramadı çünkü "howPatientAreWe: 10000" gecikme / zaman aşımı, tarayıcı içi geliştirme için çok fazla rahatsızlık yarattı. Ve daha düşük bir değere ayarlamak, zaman zaman uygulama / cihaz modunda testi geçemeyebilir. Başka bir yolu olmalıydı ...

Phonegap oluşturma hizmeti phonegap.js, uygulamanızın dosyalarını hizmete göndermeden önce dosyanın kod deponuzdan çıkarılmasını gerektirir . Bu nedenle, bir tarayıcıda mı yoksa uygulamada mı çalıştığını belirlemek için varlığını test edebilirim.

Bir başka uyarı, ben de jQueryMobile kullanıyorum, bu nedenle herhangi bir özel komut dosyası oluşturmaya başlamadan önce hem jQM hem de phonegap'in başlatılması gerekiyordu. Aşağıdaki kod, uygulama için özel index.js dosyamın başına (jQuery'den sonra, jQM'den önce) yerleştirilmiştir. Ayrıca phonegap derleme dokümanları <script src="phonegap.js"></script>, HTML'de bir yere yerleştirmeyi söylüyor . Tamamen dışarıda bırakıyorum ve varlığını test etmek için $ .getScript () kullanarak yüklüyorum.

isPhoneGap = false;
isPhoneGapReady = false;
isjQMReady = false;

$.getScript("phonegap.js")
.done(function () {
    isPhoneGap = true;
    document.addEventListener("deviceready", function () {
        console.log("phonegap ready - device/app mode");
        isPhoneGapReady = true;
        Application.checkReadyState();
    }, false);
})
.fail(function () {
    console.log("phonegap load failed - browser only");
    isPhoneGapReady = true;
    Application.checkReadyState();
});

$(document).bind("mobileinit", function () {
    Application.mobileInit();
    $(document).one("pageinit", "#Your_First_jQM_Page", function () {
        isjQMReady = true;
        Application.checkReadyState();
    });
});

Application = {
    checkReadyState: function () {
        if (isjQMReady && isPhoneGapReady) {
            Application.ready();
        }
    },
    mobileInit: function () {
        // jQM initialization settings go here
        // i.e. $.mobile.defaultPageTransition = 'slide';
    },
    ready: function () {
        // Both phonegap (if available) and jQM are fired up and ready
        // let the custom scripting begin!
    }
}

6

İlginç bir şekilde, birçok cevap, ancak bu üç seçeneği içermiyorlar:

1 - cordova.js, cordova nesnesini genel kapsamda ayarlayacaktır. Eğer oradaysa, büyük olasılıkla bir Cordova dürbününde koşuyorsunuz.

var isCordovaApp = !!window.cordova;

2 - Cordova, uygulamanızı Masaüstünüzden bir HTML belgesi açtığınız gibi çalıştıracaktır. HTTP protokolü yerine FILE kullanacaktır. Bunu tespit etmek, size uygulamanızın yerel olarak yüklendiğini varsayma şansı verecektir.

var isCordovaApp = document.URL.indexOf('http://') === -1
  && document.URL.indexOf('https://') === -1;

3 - Bağlamı algılamak için cordova betiğinin load olayını kullanın. Komut dosyası, oluşturma sürecinde kolayca kaldırılabilir veya komut dosyası yükleme işlemi bir tarayıcıda başarısız olur. Böylece bu global değişken ayarlanmayacaktır.

<script src="../cordova.js" onload="javascript:window.isCordovaApp = true;"></script>

Kredi , Adobe'den Damien Antipa'ya gidiyor


5

Bu yöntemi kullanıyorum:

debug = (window.cordova === undefined);

debugcihazda truetarayıcı ortamında olacaktır false.



3

Sorunun özü, cordova.device tanımlanmadığı sürece kodunuzun, cordova'nın cihazınızın desteklenmediğini tespit ettiğinden mi yoksa cordova'nın hala kendini hazırladığından ve cihaz hazırlığının daha sonra ateşleneceğinden mi kaynaklandığından emin olamamasıdır. (veya üçüncü seçenek: cordova düzgün yüklenmedi).

Tek çözüm, bir bekleme süresi tanımlamak ve bu sürenin sonunda kodunuzun cihazın desteklenmediğini varsayması gerektiğine karar vermektir. Keşke cordova bir yere "Desteklenen bir cihaz bulmayı denedik ve vazgeçtik" diyecek bir parametre ayarlasa da öyle görünüyor ki böyle bir parametre yok.

Bu bir kez kurulduktan sonra, desteklenen bir cihazın olmadığı durumlarda tam olarak belirli bir şey yapmak isteyebilirsiniz. Benim durumumda, cihazın uygulama pazarına bağlantıları gizlemek gibi.

Hemen hemen her durumu kapsaması gereken bu işlevi bir araya getirdim. Cihaza hazır bir işleyici, cihaza asla hazır olmayan bir işleyici ve bekleme süresi tanımlamanıza olanak tanır.

//Deals with the possibility that the code will run on a non-phoneGap supported
//device such as desktop browsers. Gives several options including waiting a while
//for cordova to load after all.
//In:
//onceReady (function) - performed as soon as deviceready fires
//patience 
//  (int) - time to wait before establishing that cordova will never load
//  (boolean false) - don't wait: assume that deviceready will never fire
//neverReady 
//  (function) - performed once it's established deviceready will never fire
//  (boolean true) - if deviceready will never fire, run onceReady anyhow
//  (boolean false or undefined) - if deviceready will never fire, do nothing
function deviceReadyOrNot(onceReady,patience,neverReady){

    if (!window.cordova){
            console.log('Cordova was not loaded when it should have been')
            if (typeof neverReady == "function"){neverReady();}
        //If phoneGap script loaded...
        } else {
            //And device is ready by now...
            if  (cordova.device){
                callback();
            //...or it's loaded but device is not ready
            } else {
                //...we might run the callback after
                if (typeof patience == "number"){
                    //Run the callback as soon as deviceready fires
                    document.addEventListener('deviceready.patience',function(){
                        if (typeof onceReady == "function"){onceReady();}
                    })
                    //Set a timeout to disable the listener
                    window.setTimeout(function(){
                        //If patience has run out, unbind the handler
                        $(document).unbind('deviceready.patience');
                        //If desired, manually run the callback right now
                        if (typeof neverReady == 'function'){neverReady();}
                    },patience);
                //...or we might just do nothing
                } else {
                    //Don't bind a deviceready handler: assume it will never happen
                    if (typeof neverReady == 'function'){neverReady();} 
                    else if (neverReady === true){onceReady();} 
                    else {
                       //Do nothing
                    }
                }
            }
    }

}

3

Bunu yapma şeklim, cordova.js'nin yalnızca tarayıcı sürümünün üzerine yazılan global bir değişken kullanmaktır. Ana html dosyanızda (genellikle index.html) sıraya bağlı aşağıdaki komut dosyalarım var:

    <script>
        var __cordovaRunningOnBrowser__ = false
    </script>
    <script src="cordova.js"></script> <!-- must be included after __cordovaRunningOnBrowser__ is initialized -->
    <script src="index.js"></script> <!-- must be included after cordova.js so that __cordovaRunningOnBrowser__ is set correctly -->

Ve içimde cordova.jsbasitçe var:

__cordovaRunningOnBrowser__ = true

Bir mobil cihaz için oluştururken, cordova.js kullanılmayacaktır (ve bunun yerine platforma özgü cordova.js dosyası kullanılacaktır), bu nedenle bu yöntem, protokoller, userAgents veya kitaplıktan bağımsız olarak% 100 doğru olma avantajına sahiptir. değişkenler (değişebilir). Cordova.js'ye eklemem gereken başka şeyler de olabilir, ancak bunların ne olduğunu henüz bilmiyorum.


Çok ilginç bir yaklaşım.

Yine de, ilk senaryoya gerçekten ihtiyacınız yok. if ( typeof __cordovaRunningOnBrowser__ !== 'undefined' ) { stuff(); } Ayarlandığını test edebilirsiniz: .. değil mi?

Doğru, tanımsız olması başka bir şeyin yanlış olduğunu gösterebilir.
BT

3

SlavikMe'nin çözümüne dayanan başka bir yol:

index.htmlPhoneGap kaynağınızdan iletilen bir sorgu parametresini kullanmanız yeterlidir. Yani, Android'de

super.loadUrl("file:///android_asset/www/index.html");

kullanım

super.loadUrl("file:///android_asset/www/index.html?phonegap=1");

SlavikMe'nin diğer platformlarda bunu nerede yapacağına dair harika bir listesi var.

O zaman index.htmlbunu kolayca yapabilirsiniz:

if (window.location.href.match(/phonegap=1/)) {
  alert("phonegap");
}
else {
  alert("not phonegap");
}

1
Cordova 3.4.1 kullanıyorum ve işte daha da basit: Sadece <content src="index.html" />config.xml dosyasındaki seçeneği <content src="index.html?cordova=1" />. Şimdiye kadar işe yarıyor gibi görünüyor ve burada önerilen en iyi çözüm.
Martin M.

2

Bir kod tabanını korumak için, kodun üzerinde çalıştığı "platform" ilgi çekici. Benim için bu "platform" üç farklı şey olabilir:

  • 0: bilgisayar tarayıcısı
  • 1: mobil tarayıcı
  • 2: phonegap / cordova

Platformu kontrol etmenin yolu:

var platform;
try {
 cordova.exec(function (param) {
   platform = 2;
  }, function (err) {}, "Echo", "echo", ["test"]);
} catch (e) {
  platform = 'ontouchstart' in document.documentElement ? 1 : 0;
}

Not:

  • Bu olmalı yalnızca cordova.js yüklendikten sonra çalıştırılmalıdır (body onload (...), $ (document) .ready (...))

  • document.documentElement içindeki 'ontouchstart', dokunmatik ekranı olan dizüstü bilgisayarlarda ve masaüstü monitörlerde mevcut olacak, böylece bir masaüstü olsa bile bir mobil tarayıcıyı bildirecektir. Daha kesin bir kontrol yapmanın farklı yolları var ama bunu kullanıyorum çünkü hala ihtiyacım olan vakaların% 99'unu hallediyor. Bu satırı her zaman daha sağlam bir şeyle değiştirebilirsiniz.


1
typeof cordova !== 'undefined'Bir istisna için balık tutmak yerine kullanmayı öneririm .
krakatoa

1

Aarons, dene

if (PhoneGap.available){
    do PhoneGap stuff;
}

Hayır yapmadım. Phonegap-1.1.0.js kaynak koduna bakın. PhoneGap.available = DeviceInfo.uuid! == tanımsız;
GeorgeW

1

GeorgeW'nin çözümü tamam, ancak gerçek cihazda bile, PhoneGap.available yalnızca PhoneGap'ın öğeleri yüklendikten sonra geçerlidir, örneğin document.addEventListener'de onDeviceReady ('deviceready', onDeviceReady, false) çağrıldıktan sonra.

O zamandan önce, eğer bilmek istiyorsanız, şunu yapabilirsiniz:

runningInPcBrowser =
    navigator.userAgent.indexOf('Chrome')  >= 0 ||
    navigator.userAgent.indexOf('Firefox') >= 0

Bu çözüm, çoğu geliştiricinin Chrome veya Firefox kullanarak geliştirdiğini varsayar.


OP, yalnızca geliştirici için değil, bir üretim web sitesi için bir çözüm arıyor.
Jesse Hattabaugh

1

Bende de aynı sorun var.

Cordova istemcisi tarafından yüklenen URL'ye # cordova = true eklemeye ve web sayfamda location.hash.indexOf ("cordova = true")> -1 için test yapmaya eğilimliyim.


Sonunda, Al Renaud'un 4. noktasında önerdiği rotaya gittim ve inşa senaryosu karar versin. Web sitesi kodunu android varlıklar klasörüne kopyalarken index.html'deki bir bayrağı kaldırır. // AÇIKLAMADAN ÇIKARMA: window._appInfo.isCordova = true; Derleme betiği index.html'yi android assets / www klasörüme kopyaladığında, // UNCOMMENT-ON-DEPLOY: dizesini kaldırmak için üzerinde ed komutunu çalıştırıyorum. # Massage index.html cordova ed "$ DEST / index.html" << - EOF 1, \ $ s / \ / \ / UNCOMMENT-ON-DEPLOY: // wq EOF
Austin France

1

Aşağıdaki en son PhoneGap / Cordova (2.1.0) ile benim için çalışıyor.

Nasıl çalışır:

  • Konsept olarak çok basit
  • Yukarıdaki zaman aşımı çözümlerinden bazılarının mantığını tersine çevirdim.
  • Device_ready olayına kaydolun ( PhoneGap belgeleri tarafından önerildiği gibi )
    • Bir zaman aşımından sonra olay hala Tetiklenmediyse, bir tarayıcı varsayımına dönün.
    • Buna karşılık, yukarıdaki diğer çözümler bazı PhoneGap özelliklerini veya diğerlerini test etmeye ve test molalarını izlemeye dayanır.

Avantajları:

  • PhoneGap tarafından önerilen device_ready olayını kullanır.
  • Mobil uygulamada gecikme yok. Device_ready olayı patladığında, devam ederiz.
  • Kullanıcı aracısı koklama yok (Uygulamamı mobil web sitesi olarak test etmeyi seviyorum, bu nedenle tarayıcı koklama benim için bir seçenek değildi).
  • Belgelenmemiş (ve dolayısıyla kırılgan) PhoneGap özelliklerine / özelliklerine güvenmek yok.
  • Bir masaüstü veya mobil tarayıcı kullanırken bile cordova.js kodunuzu kod tabanınızda tutun. Böylece, bu OP'nin sorusuna cevap verir.
  • Wytze yukarıda belirtti: 'Keşke cordova bir yerde "Desteklenen bir cihazı bulmayı denedik ve vazgeçtik" diyecek bir parametre ayarlasaydı ama öyle görünüyor ki böyle bir parametre yok.' Bu yüzden burada bir tane veriyorum.

Dezavantajları:

  • Zaman aşımları iğrenç. Ancak mobil uygulama mantığımız bir gecikmeye dayanmıyor; daha ziyade, web tarayıcısı modundayken bir yedek olarak kullanılır.

==

Yepyeni bir boş PhoneGap projesi oluşturun. Sağlanan örnek index.js'de, alttaki "uygulama" değişkenini bununla değiştirin:

var app = {
    // denotes whether we are within a mobile device (otherwise we're in a browser)
    iAmPhoneGap: false,
    // how long should we wait for PhoneGap to say the device is ready.
    howPatientAreWe: 10000,
    // id of the 'too_impatient' timeout
    timeoutID: null,
    // id of the 'impatience_remaining' interval reporting.
    impatienceProgressIntervalID: null,

    // Application Constructor
    initialize: function() {
        this.bindEvents();
    },
    // Bind Event Listeners
    //
    // Bind any events that are required on startup. Common events are:
    // `load`, `deviceready`, `offline`, and `online`.
    bindEvents: function() {
        document.addEventListener('deviceready', this.onDeviceReady, false);
        // after 10 seconds, if we still think we're NOT phonegap, give up.
        app.timeoutID = window.setTimeout(function(appReference) {
            if (!app.iAmPhoneGap) // jeepers, this has taken too long.
                // manually trigger (fudge) the receivedEvent() method.   
                appReference.receivedEvent('too_impatient');
        }, howPatientAreWe, this);
        // keep us updated on the console about how much longer to wait.
        app.impatienceProgressIntervalID = window.setInterval(function areWeThereYet() {
                if (typeof areWeThereYet.howLongLeft == "undefined") { 
                    areWeThereYet.howLongLeft = app.howPatientAreWe; // create a static variable
                } 
                areWeThereYet.howLongLeft -= 1000; // not so much longer to wait.

                console.log("areWeThereYet: Will give PhoneGap another " + areWeThereYet.howLongLeft + "ms");
            }, 1000);
    },
    // deviceready Event Handler
    //
    // The scope of `this` is the event. In order to call the `receivedEvent`
    // function, we must explicity call `app.receivedEvent(...);`
    onDeviceReady: function() {
        app.iAmPhoneGap = true; // We have a device.
        app.receivedEvent('deviceready');

        // clear the 'too_impatient' timeout .
        window.clearTimeout(app.timeoutID); 
    },
    // Update DOM on a Received Event
    receivedEvent: function(id) {
        // clear the "areWeThereYet" reporting.
        window.clearInterval(app.impatienceProgressIntervalID);
        console.log('Received Event: ' + id);
        myCustomJS(app.iAmPhoneGap); // run my application.
    }
};

app.initialize();

function myCustomJS(trueIfIAmPhoneGap) {
    // put your custom javascript here.
    alert("I am "+ (trueIfIAmPhoneGap?"PhoneGap":"a Browser"));
}

1

Birkaç ay önce uygulamamıza başlarken bu soruna rastladım, çünkü uygulamanın "browser-compatible " (bu senaryoda bazı işlevlerin engelleneceğini anlayarak: ses kaydı, pusula vb.).

100%Uygulama yürütme bağlamını ÖN-belirlemeye yönelik tek (ve yüzde 100 koşulda ısrar ediyorum) çözüm şuydu:

  • bir JS "bayrak" değişkenini doğru olarak başlatmak ve tüm web bağlamındayken bunu yanlış olarak değiştirmek;

  • bu nedenle " willIBeInPhoneGapSometimesInTheNearFuture()" gibi bir çağrı kullanabilirsiniz (bu PRE-PG'dir, elbette PG API'lerini çağırıp çağıramayacağınızı kontrol etmek için bir POST-PG yöntemine ihtiyacınız vardır, ancak bu önemsizdir).

  • Sonra " but how do you determine the execution context?" Diyorsunuz; cevap: "yapmıyorsun" (çünkü, PG'deki zeki insanlar API kodlarında bunu yapmadıkça, güvenilir bir şekilde yapabileceğinizi düşünmüyorum);

  • bunu sizin için yapan bir yapı betiği yazarsınız: iki değişkenli bir kod tabanı.


1

Değil gerçekten bir masaüstü tarayıcıda ben testi butwhen soruya bir cevap, ben sadece uygulama dispite deviceready fireing değil tarayıcı yükü yapmak için bir localStorage değerini ayarlayın.

function main() {

    // Initiating the app here.
};

/* Listen for ready events from pheongap */
document.addEventListener("deviceready", main, false);

// When testing outside ipad app, use jquerys ready event instead. 
$(function() {

    if (localStorage["notPhonegap"]) {

        main();
    }
});

1

PhoneGap Javascript dosyasını uygulamanın masaüstü sürümünden kaldırmadığınız sürece hiçbiri işe yaramaz, bu da benim bir kod tabanına sahip olma hedefimi bozar.

Başka bir seçenek de birleştirme kullanmak olabilir klasörünü , aşağıdaki ekran görüntüsüne bakın.

Platforma özel dosyalar ekleyebilir / varsayılanları geçersiz kılabilirsiniz.

(bazı senaryolarda işe yaramalı)

görüntü açıklamasını buraya girin


Başka bir deyişle: Tarayıcıyı tespit etmek yerine, masaüstü için belirli dosyaları dahil etmezsiniz / yalnızca iOS için belirli dosyalar iliştirmezsiniz.


1

Taklit cihazı etkin olsa bile masaüstü tarayıcısını algıla

Windows ve Mac makinelerde çalışır. Linux için bir çözüm bulmanız gerekiyor Ayrıntıları görüntüle

var mobileDevice = false;
if(navigator.userAgent.match(/iPhone|iPad|iPod|Android|BlackBerry|IEMobile/))
    mobileDevice = true; 

if(mobileDevice && navigator.platform.match(/Win|Mac/i))
    mobileDevice = false; // This is desktop browser emulator

if(mobileDevice) {
    // include cordova files
}

0

Aslında burada listelenen tekniklerden ikisinin bir kombinasyonunun en iyi sonucu verdiğini buldum, öncelikle cordova / phonegap'e erişilip erişilemediğini kontrol edin, ayrıca cihazın mevcut olup olmadığını kontrol edin. Şöyle:

function _initialize() {
    //do stuff
}

if (window.cordova && window.device) {
    document.addEventListener('deviceready', function () {
      _initialize();
    }, false);
} else {
   _initialize();
}

0

Bu yaklaşımı deneyin:

/**
 * Returns true if the application is running on an actual mobile device.
 */
function isOnDevice(){
    return navigator.userAgent.match(/(iPhone|iPod|iPad|Android|BlackBerry)/);
}

function isDeviceiOS(){
    return navigator.userAgent.match(/(iPhone)/);
}

/**
 * Method for invoking functions once the DOM and the device are ready. This is
 * a replacement function for the JQuery provided method i.e.
 * $(document).ready(...).
 */
function invokeOnReady(callback){
    $(document).ready(function(){
        if (isOnDevice()) {
            document.addEventListener("deviceready", callback, false);
        } else {
            invoke(callback);
        }
    });
}

0

GeorgeW ve mkprogramming'in önerdiklerinin bir kombinasyonunu kullanıyorum :

   if (!navigator.userAgent.match(/(iPhone|iPod|iPad|Android|BlackBerry)/)) {
      onDeviceReady();
   } else if (Phonegap.available){
      onDeviceReady();
   } else {
      console.log('There was an error loading Phonegap.')
   }

0

Sanırım bazı durumlarda o kadar da farklı değiller, değil mi? Ha Ha ... komik değil. Bunun bir sorun olmayacağını kim düşünmedi? Düşünceleriniz için en basit çözüm burada. Sunucunuza farklı dosyalar gönderin, ardından PhoneGap'e yaparsınız. Ayrıca, yukarıda önerilen http: kontrolünü geçici olarak kullanırdım.

var isMobileBrowserAndNotPhoneGap = (document.location.protocol == "http:");

Benim ilgilendiğim, tarayıcıların gezinme çubuğunu yukarı itmek, bu yüzden gerçekten izole edilmiş komut dosyasının etiketini silebilirim ve [DW'de] yeniden oluştur düğmesine basabilirim (yine de dağıtım için biraz temizlik olacak, bu nedenle bu görevlerden biri olabilir.) Neyse hissediyorum PG'ye basarken isMobileBrowserAndNotPhoneGap ile işleri verimli bir şekilde manuel olarak yorumlamak için iyi bir seçenektir (başka pek bir şeyin bulunmadığı düşünüldüğünde). Yine benim durumumda, bir mobil tarayıcı olduğunda gezinme çubuğunu yukarı iten (izole edilmiş kod) dosyasının etiketini basitçe sileceğim (çok daha hızlı ve daha küçük olacak). [O optimize edilmiş ancak manuel çözümün kodunu izole edebilirseniz.]


0

Biraz değiştirildi, ancak benim için herhangi bir sorun olmadan mükemmel çalışıyor.

Amaç, Cordova'yı masaüstünde değil, yalnızca gömülü cihazdayken yüklemektir, bu nedenle, bir masaüstü tarayıcısında cordova'dan tamamen kaçınıyorum. UI ve MVVM'nin test edilmesi ve geliştirilmesi ve böylece çok rahattır.

Bu kodu örneğin koyun. cordovaLoader.js dosyasında

function isEmbedded() {
    return  
    // maybe you can test for better conditions
    //&& /^file:\/{3}[^\/]/i.test(window.location.href) && 
     /ios|iphone|ipod|ipad|android/i.test(navigator.userAgent);
}

if ( isEmbedded() )
{
   var head= document.getElementsByTagName('head')[0];
   var script= document.createElement('script');
   script.type= 'text/javascript';
   script.src= 'cordova-2.7.0.js';
   head.appendChild(script);
}

Daha sonra, cordova javascript'i eklemek yerine, cordovaLoader.js'yi dahil edin

<head>
  <script src="js/cordovaLoader.js"></script>
  <script src="js/jquery.js"></script>
  <script src="js/iscroll.js"></script>
  <script src="js/knockout-2.3.0.js"></script>
</head> 

İşinizi kolaylaştırın! :)



0

PhoneGap 3.x Mobil Uygulama Geliştirme Hotshot'ta yol hakkında bilgi için

var userLocale = "en-US";
function startApp()
{
// do translations, format numbers, etc.
}
function getLocaleAndStartApp()
{
    navigator.globalization.getLocaleName (
        function (locale) {
            userLocale = locale.value;
            startApp();
        },
        function () {
            // error; start app anyway
            startApp();
        });
}
function executeWhenReady ( callback ) {
    var executed = false;
    document.addEventListener ( "deviceready", function () {
        if (!executed) {
            executed = true;
            if (typeof callback === "function") {
                callback();
            }
        }
    }, false);
    setTimeout ( function () {
        if (!executed) {
            executed = true;
            if (typeof callback === "function") {
                callback();
            }
        }
    }, 1000 );
};
executeWhenReady ( function() {
    getLocaleAndStartApp();
} );

ve YASMF çerçevesinde

https://github.com/photokandyStudios/YASMF-Next/blob/master/lib/yasmf/util/core.js#L152


0

Pencere nesnelerini deniyordum, ancak InAppBrowser'da uzak url'yi açarken işe yaramadı. Yapamadım. Dolayısıyla, bunu başarmanın en iyi ve en kolay yolu, phonegap uygulamasından açmanız gereken url'ye bir dize eklemekti. Ardından, belge konumuna eklenen dizenin olup olmadığını kontrol edin.

Aşağıda bunun için basit kod var

var ref = window.open('http://yourdomain.org#phonegap', '_blank', 'location=yes');

"#Phonegap" url'sine bir dize eklendiğini göreceksiniz. Dolayısıyla, etki alanı url'sine aşağıdaki komut dosyasını ekleyin

if(window.location.indexOf("#phonegap") > -1){
     alert("Url Loaded in the phonegap App");
}
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.