зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1104055 - fix CameraControl memory leak, r=aosmond
This commit is contained in:
Родитель
3159d55da3
Коммит
cb12b55b35
|
@ -15,11 +15,10 @@
|
|||
|
||||
using namespace mozilla;
|
||||
|
||||
nsWeakPtr CameraControlImpl::sCameraThread;
|
||||
/* static */ StaticRefPtr<nsIThread> CameraControlImpl::sCameraThread;
|
||||
|
||||
CameraControlImpl::CameraControlImpl(uint32_t aCameraId)
|
||||
CameraControlImpl::CameraControlImpl()
|
||||
: mListenerLock(PR_NewRWLock(PR_RWLOCK_RANK_NONE, "CameraControlImpl.Listeners.Lock"))
|
||||
, mCameraId(aCameraId)
|
||||
, mPreviewState(CameraControlListener::kPreviewStopped)
|
||||
, mHardwareState(CameraControlListener::kHardwareClosed)
|
||||
, mHardwareStateChangeReason(NS_OK)
|
||||
|
@ -27,7 +26,7 @@ CameraControlImpl::CameraControlImpl(uint32_t aCameraId)
|
|||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
|
||||
// reuse the same camera thread to conserve resources
|
||||
nsCOMPtr<nsIThread> ct = do_QueryReferent(sCameraThread);
|
||||
nsCOMPtr<nsIThread> ct = do_QueryInterface(sCameraThread);
|
||||
if (ct) {
|
||||
mCameraThread = ct.forget();
|
||||
} else {
|
||||
|
@ -35,9 +34,7 @@ CameraControlImpl::CameraControlImpl(uint32_t aCameraId)
|
|||
if (NS_FAILED(rv)) {
|
||||
MOZ_CRASH("Failed to create new Camera Thread");
|
||||
}
|
||||
|
||||
// keep a weak reference to the new thread
|
||||
sCameraThread = do_GetWeakReference(mCameraThread);
|
||||
sCameraThread = mCameraThread;
|
||||
}
|
||||
|
||||
// Care must be taken with the mListenerLock read-write lock to prevent
|
||||
|
@ -58,6 +55,8 @@ CameraControlImpl::CameraControlImpl(uint32_t aCameraId)
|
|||
|
||||
CameraControlImpl::~CameraControlImpl()
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
|
||||
MOZ_ASSERT(mListenerLock, "mListenerLock missing in ~CameraControlImpl()");
|
||||
if (mListenerLock) {
|
||||
PR_DestroyRWLock(mListenerLock);
|
||||
|
@ -65,12 +64,6 @@ CameraControlImpl::~CameraControlImpl()
|
|||
}
|
||||
}
|
||||
|
||||
void
|
||||
CameraControlImpl::Shutdown()
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d\n", __func__, __LINE__);
|
||||
}
|
||||
|
||||
void
|
||||
CameraControlImpl::OnHardwareStateChange(CameraControlListener::HardwareState aNewState,
|
||||
nsresult aReason)
|
||||
|
|
|
@ -28,7 +28,7 @@ namespace layers {
|
|||
class CameraControlImpl : public ICameraControl
|
||||
{
|
||||
public:
|
||||
explicit CameraControlImpl(uint32_t aCameraId);
|
||||
explicit CameraControlImpl();
|
||||
virtual void AddListener(CameraControlListener* aListener) MOZ_OVERRIDE;
|
||||
virtual void RemoveListener(CameraControlListener* aListener) MOZ_OVERRIDE;
|
||||
|
||||
|
@ -47,10 +47,6 @@ public:
|
|||
virtual nsresult StopRecording() MOZ_OVERRIDE;
|
||||
virtual nsresult ResumeContinuousFocus() MOZ_OVERRIDE;
|
||||
|
||||
uint32_t GetCameraId() { return mCameraId; }
|
||||
|
||||
virtual void Shutdown() MOZ_OVERRIDE;
|
||||
|
||||
// Event handlers called directly from outside this class.
|
||||
void OnShutter();
|
||||
void OnUserError(CameraControlListener::UserContext aContext, nsresult aError);
|
||||
|
@ -77,7 +73,7 @@ protected:
|
|||
// don't want that reference to keep the thread object around unnecessarily,
|
||||
// so we make it a weak reference. The strong dynamic references will keep
|
||||
// the thread object alive as needed.
|
||||
static nsWeakPtr sCameraThread;
|
||||
static StaticRefPtr<nsIThread> sCameraThread;
|
||||
nsCOMPtr<nsIThread> mCameraThread;
|
||||
|
||||
virtual ~CameraControlImpl();
|
||||
|
@ -128,8 +124,6 @@ protected:
|
|||
void OnShutterInternal();
|
||||
void OnClosedInternal();
|
||||
|
||||
uint32_t mCameraId;
|
||||
|
||||
CameraControlListener::CameraListenerConfiguration mCurrentConfiguration;
|
||||
|
||||
CameraControlListener::PreviewState mPreviewState;
|
||||
|
|
|
@ -136,6 +136,7 @@ void
|
|||
CameraPreviewMediaStream::Destroy()
|
||||
{
|
||||
MutexAutoLock lock(mMutex);
|
||||
mMainThreadDestroyed = true;
|
||||
DestroyImpl();
|
||||
}
|
||||
|
||||
|
|
|
@ -32,8 +32,8 @@ protected:
|
|||
* This is a stream for camera preview.
|
||||
*
|
||||
* XXX It is a temporary fix of SourceMediaStream.
|
||||
* A camera preview requests no delay and no buffering stream.
|
||||
* But the SourceMediaStream do not support it.
|
||||
* A camera preview requests no delay and no buffering stream,
|
||||
* but the SourceMediaStream does not support it.
|
||||
*/
|
||||
class CameraPreviewMediaStream : public MediaStream
|
||||
{
|
||||
|
@ -50,7 +50,7 @@ public:
|
|||
virtual void ChangeExplicitBlockerCount(int32_t aDelta) MOZ_OVERRIDE;
|
||||
virtual void AddListener(MediaStreamListener* aListener) MOZ_OVERRIDE;
|
||||
virtual void RemoveListener(MediaStreamListener* aListener) MOZ_OVERRIDE;
|
||||
virtual void Destroy();
|
||||
virtual void Destroy() MOZ_OVERRIDE;
|
||||
void OnPreviewStateChange(bool aActive);
|
||||
|
||||
void Invalidate();
|
||||
|
|
|
@ -7,15 +7,79 @@
|
|||
#include "DOMCameraCapabilities.h"
|
||||
#include "nsPIDOMWindow.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsProxyRelease.h"
|
||||
#include "mozilla/dom/CameraManagerBinding.h"
|
||||
#include "mozilla/dom/CameraCapabilitiesBinding.h"
|
||||
#include "Navigator.h"
|
||||
#include "CameraCommon.h"
|
||||
#include "ICameraControl.h"
|
||||
#include "CameraControlListener.h"
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
/**
|
||||
* CameraClosedListenerProxy and CameraClosedMessage
|
||||
*/
|
||||
template<class T>
|
||||
class CameraClosedMessage : public nsRunnable
|
||||
{
|
||||
public:
|
||||
CameraClosedMessage(nsMainThreadPtrHandle<T> aListener)
|
||||
: mListener(aListener)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
Run() MOZ_OVERRIDE
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
nsRefPtr<T> listener = mListener.get();
|
||||
if (listener) {
|
||||
listener->OnHardwareClosed();
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual ~CameraClosedMessage()
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
}
|
||||
|
||||
nsMainThreadPtrHandle<T> mListener;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
class CameraClosedListenerProxy : public CameraControlListener
|
||||
{
|
||||
public:
|
||||
CameraClosedListenerProxy(T* aListener)
|
||||
: mListener(new nsMainThreadPtrHolder<T>(aListener))
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
}
|
||||
|
||||
virtual void
|
||||
OnHardwareStateChange(HardwareState aState, nsresult aReason) MOZ_OVERRIDE
|
||||
{
|
||||
if (aState != kHardwareClosed) {
|
||||
return;
|
||||
}
|
||||
NS_DispatchToMainThread(new CameraClosedMessage<T>(mListener));
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual ~CameraClosedListenerProxy()
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
}
|
||||
|
||||
nsMainThreadPtrHandle<T> mListener;
|
||||
};
|
||||
|
||||
/**
|
||||
* CameraRecorderVideoProfile
|
||||
*/
|
||||
|
@ -96,7 +160,10 @@ CameraRecorderAudioProfile::~CameraRecorderAudioProfile()
|
|||
/**
|
||||
* CameraRecorderProfile
|
||||
*/
|
||||
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(CameraRecorderProfile, mParent)
|
||||
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(CameraRecorderProfile,
|
||||
mParent,
|
||||
mVideo,
|
||||
mAudio)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTING_ADDREF(CameraRecorderProfile)
|
||||
NS_IMPL_CYCLE_COLLECTING_RELEASE(CameraRecorderProfile)
|
||||
|
@ -136,7 +203,9 @@ CameraRecorderProfile::~CameraRecorderProfile()
|
|||
/**
|
||||
* CameraRecorderProfiles
|
||||
*/
|
||||
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(CameraRecorderProfiles, mParent)
|
||||
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(CameraRecorderProfiles,
|
||||
mParent,
|
||||
mProfiles)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTING_ADDREF(CameraRecorderProfiles)
|
||||
NS_IMPL_CYCLE_COLLECTING_RELEASE(CameraRecorderProfiles)
|
||||
|
@ -158,6 +227,10 @@ CameraRecorderProfiles::CameraRecorderProfiles(nsISupports* aParent,
|
|||
, mCameraControl(aCameraControl)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
if (mCameraControl) {
|
||||
mListener = new CameraClosedListenerProxy<CameraRecorderProfiles>(this);
|
||||
mCameraControl->AddListener(mListener);
|
||||
}
|
||||
}
|
||||
|
||||
CameraRecorderProfiles::~CameraRecorderProfiles()
|
||||
|
@ -170,6 +243,10 @@ CameraRecorderProfiles::GetSupportedNames(unsigned aFlags, nsTArray<nsString>& a
|
|||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p, flags=0x%x\n",
|
||||
__func__, __LINE__, this, aFlags);
|
||||
if (!mCameraControl) {
|
||||
aNames.Clear();
|
||||
return;
|
||||
}
|
||||
|
||||
nsresult rv = mCameraControl->GetRecorderProfiles(aNames);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
|
@ -182,6 +259,9 @@ CameraRecorderProfiles::NamedGetter(const nsAString& aName, bool& aFound)
|
|||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p, name='%s'\n", __func__, __LINE__, this,
|
||||
NS_ConvertUTF16toUTF8(aName).get());
|
||||
if (!mCameraControl) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
CameraRecorderProfile* profile = mProfiles.GetWeak(aName, &aFound);
|
||||
if (!aFound || !profile) {
|
||||
|
@ -204,10 +284,25 @@ CameraRecorderProfiles::NameIsEnumerable(const nsAString& aName)
|
|||
return true;
|
||||
}
|
||||
|
||||
void
|
||||
CameraRecorderProfiles::OnHardwareClosed()
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
if (mCameraControl) {
|
||||
mCameraControl->RemoveListener(mListener);
|
||||
mCameraControl = nullptr;
|
||||
}
|
||||
mListener = nullptr;
|
||||
}
|
||||
|
||||
/**
|
||||
* CameraCapabilities
|
||||
*/
|
||||
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(CameraCapabilities, mWindow)
|
||||
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(CameraCapabilities,
|
||||
mWindow,
|
||||
mRecorderProfiles)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTING_ADDREF(CameraCapabilities)
|
||||
NS_IMPL_CYCLE_COLLECTING_RELEASE(CameraCapabilities)
|
||||
|
@ -236,7 +331,10 @@ CameraCapabilities::CameraCapabilities(nsPIDOMWindow* aWindow,
|
|||
, mCameraControl(aCameraControl)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_COUNT_CTOR(CameraCapabilities);
|
||||
if (mCameraControl) {
|
||||
mListener = new CameraClosedListenerProxy<CameraCapabilities>(this);
|
||||
mCameraControl->AddListener(mListener);
|
||||
}
|
||||
}
|
||||
|
||||
CameraCapabilities::~CameraCapabilities()
|
||||
|
@ -245,6 +343,19 @@ CameraCapabilities::~CameraCapabilities()
|
|||
MOZ_COUNT_DTOR(CameraCapabilities);
|
||||
}
|
||||
|
||||
void
|
||||
CameraCapabilities::OnHardwareClosed()
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
if (mCameraControl) {
|
||||
mCameraControl->RemoveListener(mListener);
|
||||
mCameraControl = nullptr;
|
||||
}
|
||||
mListener = nullptr;
|
||||
}
|
||||
|
||||
JSObject*
|
||||
CameraCapabilities::WrapObject(JSContext* aCx)
|
||||
{
|
||||
|
@ -262,6 +373,10 @@ CameraCapabilities::WrapObject(JSContext* aCx)
|
|||
nsresult
|
||||
CameraCapabilities::TranslateToDictionary(uint32_t aKey, nsTArray<CameraSize>& aSizes)
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return NS_ERROR_NOT_AVAILABLE;
|
||||
}
|
||||
|
||||
nsresult rv;
|
||||
nsTArray<ICameraControl::Size> sizes;
|
||||
|
||||
|
@ -328,6 +443,10 @@ CameraCapabilities::GetVideoSizes(nsTArray<dom::CameraSize>& retval)
|
|||
void
|
||||
CameraCapabilities::GetFileFormats(nsTArray<nsString>& retval)
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mFileFormats.Length() == 0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_PICTUREFORMATS,
|
||||
mFileFormats);
|
||||
|
@ -339,6 +458,10 @@ CameraCapabilities::GetFileFormats(nsTArray<nsString>& retval)
|
|||
void
|
||||
CameraCapabilities::GetWhiteBalanceModes(nsTArray<nsString>& retval)
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mWhiteBalanceModes.Length() == 0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_WHITEBALANCES,
|
||||
mWhiteBalanceModes);
|
||||
|
@ -350,6 +473,10 @@ CameraCapabilities::GetWhiteBalanceModes(nsTArray<nsString>& retval)
|
|||
void
|
||||
CameraCapabilities::GetSceneModes(nsTArray<nsString>& retval)
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mSceneModes.Length() == 0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_SCENEMODES,
|
||||
mSceneModes);
|
||||
|
@ -361,6 +488,10 @@ CameraCapabilities::GetSceneModes(nsTArray<nsString>& retval)
|
|||
void
|
||||
CameraCapabilities::GetEffects(nsTArray<nsString>& retval)
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mEffects.Length() == 0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_EFFECTS,
|
||||
mEffects);
|
||||
|
@ -372,6 +503,10 @@ CameraCapabilities::GetEffects(nsTArray<nsString>& retval)
|
|||
void
|
||||
CameraCapabilities::GetFlashModes(nsTArray<nsString>& retval)
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mFlashModes.Length() == 0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_FLASHMODES,
|
||||
mFlashModes);
|
||||
|
@ -383,6 +518,10 @@ CameraCapabilities::GetFlashModes(nsTArray<nsString>& retval)
|
|||
void
|
||||
CameraCapabilities::GetFocusModes(nsTArray<nsString>& retval)
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mFocusModes.Length() == 0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_FOCUSMODES,
|
||||
mFocusModes);
|
||||
|
@ -394,6 +533,10 @@ CameraCapabilities::GetFocusModes(nsTArray<nsString>& retval)
|
|||
void
|
||||
CameraCapabilities::GetZoomRatios(nsTArray<double>& retval)
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mZoomRatios.Length() == 0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_ZOOMRATIOS,
|
||||
mZoomRatios);
|
||||
|
@ -405,6 +548,10 @@ CameraCapabilities::GetZoomRatios(nsTArray<double>& retval)
|
|||
uint32_t
|
||||
CameraCapabilities::MaxFocusAreas()
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (mMaxFocusAreas == 0) {
|
||||
int32_t areas;
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_MAXFOCUSAREAS,
|
||||
|
@ -418,6 +565,10 @@ CameraCapabilities::MaxFocusAreas()
|
|||
uint32_t
|
||||
CameraCapabilities::MaxMeteringAreas()
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (mMaxMeteringAreas == 0) {
|
||||
int32_t areas;
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_MAXMETERINGAREAS,
|
||||
|
@ -431,6 +582,10 @@ CameraCapabilities::MaxMeteringAreas()
|
|||
uint32_t
|
||||
CameraCapabilities::MaxDetectedFaces()
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (mMaxDetectedFaces == 0) {
|
||||
int32_t faces;
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_MAXDETECTEDFACES,
|
||||
|
@ -444,6 +599,10 @@ CameraCapabilities::MaxDetectedFaces()
|
|||
double
|
||||
CameraCapabilities::MinExposureCompensation()
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return 0.0;
|
||||
}
|
||||
|
||||
if (mMinExposureCompensation == 0.0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_MINEXPOSURECOMPENSATION,
|
||||
mMinExposureCompensation);
|
||||
|
@ -455,6 +614,10 @@ CameraCapabilities::MinExposureCompensation()
|
|||
double
|
||||
CameraCapabilities::MaxExposureCompensation()
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return 0.0;
|
||||
}
|
||||
|
||||
if (mMaxExposureCompensation == 0.0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_MAXEXPOSURECOMPENSATION,
|
||||
mMaxExposureCompensation);
|
||||
|
@ -466,6 +629,10 @@ CameraCapabilities::MaxExposureCompensation()
|
|||
double
|
||||
CameraCapabilities::ExposureCompensationStep()
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return 0.0;
|
||||
}
|
||||
|
||||
if (mExposureCompensationStep == 0.0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_EXPOSURECOMPENSATIONSTEP,
|
||||
mExposureCompensationStep);
|
||||
|
@ -477,6 +644,10 @@ CameraCapabilities::ExposureCompensationStep()
|
|||
CameraRecorderProfiles*
|
||||
CameraCapabilities::RecorderProfiles()
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
nsRefPtr<CameraRecorderProfiles> profiles = mRecorderProfiles;
|
||||
if (!mRecorderProfiles) {
|
||||
profiles = new CameraRecorderProfiles(this, mCameraControl);
|
||||
|
@ -488,6 +659,10 @@ CameraCapabilities::RecorderProfiles()
|
|||
void
|
||||
CameraCapabilities::GetIsoModes(nsTArray<nsString>& retval)
|
||||
{
|
||||
if (NS_WARN_IF(!mCameraControl)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mIsoModes.Length() == 0) {
|
||||
nsresult rv = mCameraControl->Get(CAMERA_PARAM_SUPPORTED_ISOMODES,
|
||||
mIsoModes);
|
||||
|
|
|
@ -146,6 +146,8 @@ private:
|
|||
/**
|
||||
* CameraRecorderProfiles
|
||||
*/
|
||||
template<class T> class CameraClosedListenerProxy;
|
||||
|
||||
class CameraRecorderProfiles MOZ_FINAL : public nsISupports
|
||||
, public nsWrapperCache
|
||||
{
|
||||
|
@ -162,12 +164,15 @@ public:
|
|||
bool NameIsEnumerable(const nsAString& aName);
|
||||
void GetSupportedNames(unsigned aFlags, nsTArray<nsString>& aNames);
|
||||
|
||||
virtual void OnHardwareClosed();
|
||||
|
||||
protected:
|
||||
virtual ~CameraRecorderProfiles();
|
||||
|
||||
nsCOMPtr<nsISupports> mParent;
|
||||
nsRefPtr<ICameraControl> mCameraControl;
|
||||
nsRefPtrHashtable<nsStringHashKey, CameraRecorderProfile> mProfiles;
|
||||
nsRefPtr<CameraClosedListenerProxy<CameraRecorderProfiles>> mListener;
|
||||
|
||||
private:
|
||||
DISALLOW_EVIL_CONSTRUCTORS(CameraRecorderProfiles);
|
||||
|
@ -218,6 +223,8 @@ public:
|
|||
|
||||
CameraRecorderProfiles* RecorderProfiles();
|
||||
|
||||
virtual void OnHardwareClosed();
|
||||
|
||||
protected:
|
||||
~CameraCapabilities();
|
||||
|
||||
|
@ -249,6 +256,7 @@ protected:
|
|||
nsRefPtr<nsPIDOMWindow> mWindow;
|
||||
nsRefPtr<ICameraControl> mCameraControl;
|
||||
nsRefPtr<CameraRecorderProfiles> mRecorderProfiles;
|
||||
nsRefPtr<CameraClosedListenerProxy<CameraCapabilities>> mListener;
|
||||
|
||||
private:
|
||||
DISALLOW_EVIL_CONSTRUCTORS(CameraCapabilities);
|
||||
|
|
|
@ -54,13 +54,19 @@ StaticRefPtr<ICameraControl> nsDOMCameraControl::sCachedCameraControl;
|
|||
#endif
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(nsDOMCameraControl)
|
||||
NS_INTERFACE_MAP_ENTRY(nsISupports)
|
||||
NS_INTERFACE_MAP_ENTRY(nsISupportsWeakReference)
|
||||
// nsISupports is an ambiguous base of nsDOMCameraControl
|
||||
// so we have to work around that.
|
||||
if ( aIID.Equals(NS_GET_IID(nsDOMCameraControl)) )
|
||||
foundInterface = static_cast<nsISupports*>(static_cast<void*>(this));
|
||||
else
|
||||
NS_INTERFACE_MAP_END_INHERITING(DOMMediaStream)
|
||||
|
||||
NS_IMPL_ADDREF_INHERITED(nsDOMCameraControl, DOMMediaStream)
|
||||
NS_IMPL_RELEASE_INHERITED(nsDOMCameraControl, DOMMediaStream)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_INHERITED(nsDOMCameraControl, DOMMediaStream,
|
||||
mAudioChannelAgent,
|
||||
mCapabilities,
|
||||
mWindow,
|
||||
mGetCameraPromise,
|
||||
|
@ -133,7 +139,7 @@ nsDOMCameraControl::DOMCameraConfiguration::~DOMCameraConfiguration()
|
|||
}
|
||||
|
||||
#ifdef MOZ_WIDGET_GONK
|
||||
// This shoudl be long enough for even our slowest platforms.
|
||||
// This should be long enough for even our slowest platforms.
|
||||
static const unsigned long kCachedCameraTimeoutMs = 3500;
|
||||
|
||||
// Open the battery-door-facing camera by default.
|
||||
|
@ -383,88 +389,97 @@ nsDOMCameraControl::Get(uint32_t aKey, nsTArray<CameraRegion>& aValue)
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
#define THROW_IF_NO_CAMERACONTROL(...) \
|
||||
do { \
|
||||
if (!mCameraControl) { \
|
||||
DOM_CAMERA_LOGW("mCameraControl is null at %s:%d\n", __func__, __LINE__); \
|
||||
aRv = NS_ERROR_NOT_AVAILABLE; \
|
||||
return __VA_ARGS__; \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
void
|
||||
nsDOMCameraControl::GetEffect(nsString& aEffect, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_EFFECT, aEffect);
|
||||
}
|
||||
void
|
||||
nsDOMCameraControl::SetEffect(const nsAString& aEffect, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_EFFECT, aEffect);
|
||||
}
|
||||
|
||||
void
|
||||
nsDOMCameraControl::GetWhiteBalanceMode(nsString& aWhiteBalanceMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_WHITEBALANCE, aWhiteBalanceMode);
|
||||
}
|
||||
void
|
||||
nsDOMCameraControl::SetWhiteBalanceMode(const nsAString& aWhiteBalanceMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_WHITEBALANCE, aWhiteBalanceMode);
|
||||
}
|
||||
|
||||
void
|
||||
nsDOMCameraControl::GetSceneMode(nsString& aSceneMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_SCENEMODE, aSceneMode);
|
||||
}
|
||||
void
|
||||
nsDOMCameraControl::SetSceneMode(const nsAString& aSceneMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_SCENEMODE, aSceneMode);
|
||||
}
|
||||
|
||||
void
|
||||
nsDOMCameraControl::GetFlashMode(nsString& aFlashMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_FLASHMODE, aFlashMode);
|
||||
}
|
||||
void
|
||||
nsDOMCameraControl::SetFlashMode(const nsAString& aFlashMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_FLASHMODE, aFlashMode);
|
||||
}
|
||||
|
||||
void
|
||||
nsDOMCameraControl::GetFocusMode(nsString& aFocusMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_FOCUSMODE, aFocusMode);
|
||||
}
|
||||
void
|
||||
nsDOMCameraControl::SetFocusMode(const nsAString& aFocusMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_FOCUSMODE, aFocusMode);
|
||||
}
|
||||
|
||||
void
|
||||
nsDOMCameraControl::GetIsoMode(nsString& aIsoMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_ISOMODE, aIsoMode);
|
||||
}
|
||||
void
|
||||
nsDOMCameraControl::SetIsoMode(const nsAString& aIsoMode, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_ISOMODE, aIsoMode);
|
||||
}
|
||||
|
||||
double
|
||||
nsDOMCameraControl::GetPictureQuality(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL(1.0);
|
||||
|
||||
double quality;
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_PICTURE_QUALITY, quality);
|
||||
|
@ -473,14 +488,14 @@ nsDOMCameraControl::GetPictureQuality(ErrorResult& aRv)
|
|||
void
|
||||
nsDOMCameraControl::SetPictureQuality(double aQuality, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_PICTURE_QUALITY, aQuality);
|
||||
}
|
||||
|
||||
double
|
||||
nsDOMCameraControl::GetZoom(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL(1.0);
|
||||
|
||||
double zoom = 1.0;
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_ZOOM, zoom);
|
||||
|
@ -490,7 +505,7 @@ nsDOMCameraControl::GetZoom(ErrorResult& aRv)
|
|||
void
|
||||
nsDOMCameraControl::SetZoom(double aZoom, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_ZOOM, aZoom);
|
||||
}
|
||||
|
||||
|
@ -521,6 +536,8 @@ nsDOMCameraControl::SetFocusAreas(const Optional<Sequence<CameraRegion> >& aFocu
|
|||
void
|
||||
nsDOMCameraControl::GetPictureSize(CameraSize& aSize, ErrorResult& aRv)
|
||||
{
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
|
||||
ICameraControl::Size size;
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_PICTURE_SIZE, size);
|
||||
if (aRv.Failed()) {
|
||||
|
@ -534,6 +551,7 @@ nsDOMCameraControl::GetPictureSize(CameraSize& aSize, ErrorResult& aRv)
|
|||
void
|
||||
nsDOMCameraControl::SetPictureSize(const CameraSize& aSize, ErrorResult& aRv)
|
||||
{
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
ICameraControl::Size s = { aSize.mWidth, aSize.mHeight };
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_PICTURE_SIZE, s);
|
||||
}
|
||||
|
@ -541,6 +559,7 @@ nsDOMCameraControl::SetPictureSize(const CameraSize& aSize, ErrorResult& aRv)
|
|||
void
|
||||
nsDOMCameraControl::GetThumbnailSize(CameraSize& aSize, ErrorResult& aRv)
|
||||
{
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
ICameraControl::Size size;
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_THUMBNAILSIZE, size);
|
||||
if (aRv.Failed()) {
|
||||
|
@ -554,6 +573,7 @@ nsDOMCameraControl::GetThumbnailSize(CameraSize& aSize, ErrorResult& aRv)
|
|||
void
|
||||
nsDOMCameraControl::SetThumbnailSize(const CameraSize& aSize, ErrorResult& aRv)
|
||||
{
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
ICameraControl::Size s = { aSize.mWidth, aSize.mHeight };
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_THUMBNAILSIZE, s);
|
||||
}
|
||||
|
@ -561,7 +581,7 @@ nsDOMCameraControl::SetThumbnailSize(const CameraSize& aSize, ErrorResult& aRv)
|
|||
double
|
||||
nsDOMCameraControl::GetFocalLength(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL(0.0);
|
||||
|
||||
double focalLength;
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_FOCALLENGTH, focalLength);
|
||||
|
@ -571,7 +591,7 @@ nsDOMCameraControl::GetFocalLength(ErrorResult& aRv)
|
|||
double
|
||||
nsDOMCameraControl::GetFocusDistanceNear(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL(0.0);
|
||||
|
||||
double distance;
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_FOCUSDISTANCENEAR, distance);
|
||||
|
@ -581,7 +601,7 @@ nsDOMCameraControl::GetFocusDistanceNear(ErrorResult& aRv)
|
|||
double
|
||||
nsDOMCameraControl::GetFocusDistanceOptimum(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL(0.0);
|
||||
|
||||
double distance;
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_FOCUSDISTANCEOPTIMUM, distance);
|
||||
|
@ -591,7 +611,7 @@ nsDOMCameraControl::GetFocusDistanceOptimum(ErrorResult& aRv)
|
|||
double
|
||||
nsDOMCameraControl::GetFocusDistanceFar(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL(0.0);
|
||||
|
||||
double distance;
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_FOCUSDISTANCEFAR, distance);
|
||||
|
@ -601,14 +621,14 @@ nsDOMCameraControl::GetFocusDistanceFar(ErrorResult& aRv)
|
|||
void
|
||||
nsDOMCameraControl::SetExposureCompensation(double aCompensation, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->Set(CAMERA_PARAM_EXPOSURECOMPENSATION, aCompensation);
|
||||
}
|
||||
|
||||
double
|
||||
nsDOMCameraControl::GetExposureCompensation(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
THROW_IF_NO_CAMERACONTROL(0.0);
|
||||
|
||||
double compensation;
|
||||
aRv = mCameraControl->Get(CAMERA_PARAM_EXPOSURECOMPENSATION, compensation);
|
||||
|
@ -618,18 +638,22 @@ nsDOMCameraControl::GetExposureCompensation(ErrorResult& aRv)
|
|||
int32_t
|
||||
nsDOMCameraControl::SensorAngle()
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
|
||||
int32_t angle = 0;
|
||||
mCameraControl->Get(CAMERA_PARAM_SENSORANGLE, angle);
|
||||
if (mCameraControl) {
|
||||
mCameraControl->Get(CAMERA_PARAM_SENSORANGLE, angle);
|
||||
}
|
||||
return angle;
|
||||
}
|
||||
|
||||
already_AddRefed<dom::CameraCapabilities>
|
||||
nsDOMCameraControl::Capabilities()
|
||||
{
|
||||
nsRefPtr<CameraCapabilities> caps = mCapabilities;
|
||||
if (!mCameraControl) {
|
||||
DOM_CAMERA_LOGW("mCameraControl is null at %s:%d\n", __func__, __LINE__);
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
nsRefPtr<CameraCapabilities> caps = mCapabilities;
|
||||
if (!caps) {
|
||||
caps = new CameraCapabilities(mWindow, mCameraControl);
|
||||
mCapabilities = caps;
|
||||
|
@ -645,7 +669,7 @@ nsDOMCameraControl::StartRecording(const CameraStartRecordingOptions& aOptions,
|
|||
const nsAString& aFilename,
|
||||
ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
|
||||
nsRefPtr<Promise> promise = CreatePromise(aRv);
|
||||
if (aRv.Failed()) {
|
||||
|
@ -694,7 +718,9 @@ nsDOMCameraControl::OnCreatedFileDescriptor(bool aSucceeded)
|
|||
{
|
||||
nsresult rv = NS_ERROR_FAILURE;
|
||||
|
||||
if (aSucceeded && mDSFileDescriptor->mFileDescriptor.IsValid()) {
|
||||
if (!mCameraControl) {
|
||||
rv = NS_ERROR_NOT_AVAILABLE;
|
||||
} else if (aSucceeded && mDSFileDescriptor->mFileDescriptor.IsValid()) {
|
||||
ICameraControl::StartRecordingOptions o;
|
||||
|
||||
o.rotation = mOptions.mRotation;
|
||||
|
@ -722,7 +748,8 @@ nsDOMCameraControl::OnCreatedFileDescriptor(bool aSucceeded)
|
|||
void
|
||||
nsDOMCameraControl::StopRecording(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
|
||||
#ifdef MOZ_B2G
|
||||
if (mAudioChannelAgent) {
|
||||
|
@ -737,7 +764,8 @@ nsDOMCameraControl::StopRecording(ErrorResult& aRv)
|
|||
void
|
||||
nsDOMCameraControl::ResumePreview(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->StartPreview();
|
||||
}
|
||||
|
||||
|
@ -745,7 +773,8 @@ already_AddRefed<Promise>
|
|||
nsDOMCameraControl::SetConfiguration(const CameraConfiguration& aConfiguration,
|
||||
ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
THROW_IF_NO_CAMERACONTROL(nullptr);
|
||||
|
||||
nsRefPtr<Promise> promise = CreatePromise(aRv);
|
||||
if (aRv.Failed()) {
|
||||
|
@ -779,7 +808,8 @@ nsDOMCameraControl::SetConfiguration(const CameraConfiguration& aConfiguration,
|
|||
already_AddRefed<Promise>
|
||||
nsDOMCameraControl::AutoFocus(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
THROW_IF_NO_CAMERACONTROL(nullptr);
|
||||
|
||||
nsRefPtr<Promise> promise = mAutoFocusPromise.forget();
|
||||
if (promise) {
|
||||
|
@ -807,14 +837,16 @@ nsDOMCameraControl::AutoFocus(ErrorResult& aRv)
|
|||
void
|
||||
nsDOMCameraControl::StartFaceDetection(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->StartFaceDetection();
|
||||
}
|
||||
|
||||
void
|
||||
nsDOMCameraControl::StopFaceDetection(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->StopFaceDetection();
|
||||
}
|
||||
|
||||
|
@ -822,7 +854,8 @@ already_AddRefed<Promise>
|
|||
nsDOMCameraControl::TakePicture(const CameraPictureOptions& aOptions,
|
||||
ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
THROW_IF_NO_CAMERACONTROL(nullptr);
|
||||
|
||||
nsRefPtr<Promise> promise = CreatePromise(aRv);
|
||||
if (aRv.Failed()) {
|
||||
|
@ -871,34 +904,45 @@ nsDOMCameraControl::TakePicture(const CameraPictureOptions& aOptions,
|
|||
already_AddRefed<Promise>
|
||||
nsDOMCameraControl::ReleaseHardware(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGI("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
|
||||
nsRefPtr<Promise> promise = CreatePromise(aRv);
|
||||
if (aRv.Failed()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (!mCameraControl) {
|
||||
// Always succeed if the camera instance is already closed.
|
||||
promise->MaybeResolve(JS::UndefinedHandleValue);
|
||||
return promise.forget();
|
||||
}
|
||||
|
||||
aRv = mCameraControl->Stop();
|
||||
if (aRv.Failed()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// Once we stop the camera, there's nothing we can do with it,
|
||||
// so we can throw away this reference. (This won't prevent us
|
||||
// from receiving the last underlying events.)
|
||||
mCameraControl = nullptr;
|
||||
mReleasePromise = promise;
|
||||
|
||||
return promise.forget();
|
||||
}
|
||||
|
||||
void
|
||||
nsDOMCameraControl::ResumeContinuousFocus(ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
THROW_IF_NO_CAMERACONTROL();
|
||||
aRv = mCameraControl->ResumeContinuousFocus();
|
||||
}
|
||||
|
||||
void
|
||||
nsDOMCameraControl::Shutdown()
|
||||
{
|
||||
DOM_CAMERA_LOGI("%s:%d\n", __func__, __LINE__);
|
||||
MOZ_ASSERT(mCameraControl);
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
|
||||
// Remove any pending solicited event handlers; these
|
||||
// reference our window object, which in turn references
|
||||
|
@ -910,7 +954,10 @@ nsDOMCameraControl::Shutdown()
|
|||
AbortPromise(mReleasePromise);
|
||||
AbortPromise(mSetConfigurationPromise);
|
||||
|
||||
mCameraControl->Shutdown();
|
||||
if (mCameraControl) {
|
||||
mCameraControl->Stop();
|
||||
mCameraControl = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
nsresult
|
||||
|
@ -986,7 +1033,9 @@ void
|
|||
nsDOMCameraControl::OnHardwareStateChange(CameraControlListener::HardwareState aState,
|
||||
nsresult aReason)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
ErrorResult ignored;
|
||||
|
||||
switch (aState) {
|
||||
|
@ -1058,15 +1107,15 @@ nsDOMCameraControl::OnHardwareStateChange(CameraControlListener::HardwareState a
|
|||
void
|
||||
nsDOMCameraControl::OnShutter()
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
DOM_CAMERA_LOGI("DOM ** SNAP **\n");
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
DispatchTrustedEvent(NS_LITERAL_STRING("shutter"));
|
||||
}
|
||||
|
||||
void
|
||||
nsDOMCameraControl::OnPreviewStateChange(CameraControlListener::PreviewState aState)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
mPreviewState = aState;
|
||||
|
@ -1089,6 +1138,7 @@ nsDOMCameraControl::OnRecorderStateChange(CameraControlListener::RecorderState a
|
|||
int32_t aArg, int32_t aTrackNum)
|
||||
{
|
||||
// For now, we do nothing with 'aStatus' and 'aTrackNum'.
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
ErrorResult ignored;
|
||||
|
@ -1148,6 +1198,7 @@ nsDOMCameraControl::OnRecorderStateChange(CameraControlListener::RecorderState a
|
|||
void
|
||||
nsDOMCameraControl::OnConfigurationChange(DOMCameraConfiguration* aConfiguration)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
MOZ_ASSERT(aConfiguration != nullptr);
|
||||
|
||||
|
@ -1174,7 +1225,7 @@ nsDOMCameraControl::OnConfigurationChange(DOMCameraConfiguration* aConfiguration
|
|||
CameraConfigurationEventInit eventInit;
|
||||
eventInit.mMode = mCurrentConfiguration->mMode;
|
||||
eventInit.mRecorderProfile = mCurrentConfiguration->mRecorderProfile;
|
||||
eventInit.mPreviewSize = new DOMRect(this, 0, 0,
|
||||
eventInit.mPreviewSize = new DOMRect(static_cast<DOMMediaStream*>(this), 0, 0,
|
||||
mCurrentConfiguration->mPreviewSize.mWidth,
|
||||
mCurrentConfiguration->mPreviewSize.mHeight);
|
||||
|
||||
|
@ -1189,6 +1240,7 @@ nsDOMCameraControl::OnConfigurationChange(DOMCameraConfiguration* aConfiguration
|
|||
void
|
||||
nsDOMCameraControl::OnAutoFocusComplete(bool aAutoFocusSucceeded)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
nsRefPtr<Promise> promise = mAutoFocusPromise.forget();
|
||||
|
@ -1206,6 +1258,7 @@ nsDOMCameraControl::OnAutoFocusComplete(bool aAutoFocusSucceeded)
|
|||
void
|
||||
nsDOMCameraControl::OnAutoFocusMoving(bool aIsMoving)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
if (aIsMoving) {
|
||||
|
@ -1225,7 +1278,7 @@ nsDOMCameraControl::OnFacesDetected(const nsTArray<ICameraControl::Face>& aFaces
|
|||
if (faces.SetCapacity(len)) {
|
||||
nsRefPtr<DOMCameraDetectedFace> f;
|
||||
for (uint32_t i = 0; i < len; ++i) {
|
||||
f = new DOMCameraDetectedFace(this, aFaces[i]);
|
||||
f = new DOMCameraDetectedFace(static_cast<DOMMediaStream*>(this), aFaces[i]);
|
||||
*faces.AppendElement() = f.forget().take();
|
||||
}
|
||||
}
|
||||
|
@ -1244,6 +1297,7 @@ nsDOMCameraControl::OnFacesDetected(const nsTArray<ICameraControl::Face>& aFaces
|
|||
void
|
||||
nsDOMCameraControl::OnTakePictureComplete(nsIDOMBlob* aPicture)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p\n", __func__, __LINE__, this);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
MOZ_ASSERT(aPicture);
|
||||
|
||||
|
@ -1267,7 +1321,8 @@ nsDOMCameraControl::OnTakePictureComplete(nsIDOMBlob* aPicture)
|
|||
void
|
||||
nsDOMCameraControl::OnUserError(CameraControlListener::UserContext aContext, nsresult aError)
|
||||
{
|
||||
DOM_CAMERA_LOGI("DOM OnUserError aContext=%u, aError=0x%x\n", aContext, aError);
|
||||
DOM_CAMERA_LOGI("DOM OnUserError : this=%paContext=%u, aError=0x%x\n",
|
||||
this, aContext, aError);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
nsRefPtr<Promise> promise;
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
#include "nsHashPropertyBag.h"
|
||||
#include "DeviceStorage.h"
|
||||
#include "DOMCameraControlListener.h"
|
||||
#include "nsWeakReference.h"
|
||||
#ifdef MOZ_WIDGET_GONK
|
||||
#include "nsITimer.h"
|
||||
#endif
|
||||
|
@ -39,10 +40,17 @@ namespace dom {
|
|||
class ErrorResult;
|
||||
class StartRecordingHelper;
|
||||
|
||||
#define NS_DOM_CAMERA_CONTROL_CID \
|
||||
{ 0x3700c096, 0xf920, 0x438d, \
|
||||
{ 0x8b, 0x3f, 0x15, 0xb3, 0xc9, 0x96, 0x23, 0x62 } }
|
||||
|
||||
// Main camera control.
|
||||
class nsDOMCameraControl MOZ_FINAL : public DOMMediaStream
|
||||
, public nsSupportsWeakReference
|
||||
{
|
||||
public:
|
||||
NS_DECLARE_STATIC_IID_ACCESSOR(NS_DOM_CAMERA_CONTROL_CID)
|
||||
|
||||
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsDOMCameraControl, DOMMediaStream)
|
||||
NS_DECL_ISUPPORTS_INHERITED
|
||||
|
||||
|
@ -115,6 +123,8 @@ public:
|
|||
|
||||
virtual JSObject* WrapObject(JSContext* aCx) MOZ_OVERRIDE;
|
||||
|
||||
operator nsISupports*() { return static_cast<DOMMediaStream*>(this); }
|
||||
|
||||
#ifdef MOZ_WIDGET_GONK
|
||||
static void PreinitCameraHardware();
|
||||
static void DiscardCachedCameraInstance(nsITimer* aTimer, void* aClosure);
|
||||
|
@ -222,6 +232,8 @@ private:
|
|||
nsDOMCameraControl& operator=(const nsDOMCameraControl&) MOZ_DELETE;
|
||||
};
|
||||
|
||||
NS_DEFINE_STATIC_IID_ACCESSOR(nsDOMCameraControl, NS_DOM_CAMERA_CONTROL_CID)
|
||||
|
||||
} // namespace mozilla
|
||||
|
||||
#endif // DOM_CAMERA_DOMCAMERACONTROL_H
|
||||
|
|
|
@ -15,7 +15,8 @@ using namespace mozilla::dom;
|
|||
|
||||
DOMCameraControlListener::DOMCameraControlListener(nsDOMCameraControl* aDOMCameraControl,
|
||||
CameraPreviewMediaStream* aStream)
|
||||
: mDOMCameraControl(new nsMainThreadPtrHolder<nsDOMCameraControl>(aDOMCameraControl))
|
||||
: mDOMCameraControl(
|
||||
new nsMainThreadPtrHolder<nsISupports>(static_cast<DOMMediaStream*>(aDOMCameraControl)))
|
||||
, mStream(aStream)
|
||||
{
|
||||
DOM_CAMERA_LOGT("%s:%d : this=%p, camera=%p, stream=%p\n",
|
||||
|
@ -31,7 +32,7 @@ DOMCameraControlListener::~DOMCameraControlListener()
|
|||
class DOMCameraControlListener::DOMCallback : public nsRunnable
|
||||
{
|
||||
public:
|
||||
explicit DOMCallback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl)
|
||||
explicit DOMCallback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl)
|
||||
: mDOMCameraControl(aDOMCameraControl)
|
||||
{
|
||||
MOZ_COUNT_CTOR(DOMCameraControlListener::DOMCallback);
|
||||
|
@ -51,15 +52,17 @@ public:
|
|||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
nsRefPtr<nsDOMCameraControl> camera = mDOMCameraControl.get();
|
||||
if (camera) {
|
||||
RunCallback(camera);
|
||||
nsRefPtr<nsDOMCameraControl> camera = do_QueryObject(mDOMCameraControl.get());
|
||||
if (!camera) {
|
||||
DOM_CAMERA_LOGE("do_QueryObject failed to get an nsDOMCameraControl\n");
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
RunCallback(camera);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
protected:
|
||||
nsMainThreadPtrHandle<nsDOMCameraControl> mDOMCameraControl;
|
||||
nsMainThreadPtrHandle<nsISupports> mDOMCameraControl;
|
||||
};
|
||||
|
||||
// Specific callback handlers
|
||||
|
@ -70,7 +73,7 @@ DOMCameraControlListener::OnHardwareStateChange(HardwareState aState,
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl,
|
||||
Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl,
|
||||
HardwareState aState, nsresult aReason)
|
||||
: DOMCallback(aDOMCameraControl)
|
||||
, mState(aState)
|
||||
|
@ -97,7 +100,7 @@ DOMCameraControlListener::OnPreviewStateChange(PreviewState aState)
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl,
|
||||
Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl,
|
||||
PreviewState aState)
|
||||
: DOMCallback(aDOMCameraControl)
|
||||
, mState(aState)
|
||||
|
@ -151,7 +154,7 @@ DOMCameraControlListener::OnRecorderStateChange(RecorderState aState,
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl,
|
||||
Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl,
|
||||
RecorderState aState,
|
||||
int32_t aStatus,
|
||||
int32_t aTrackNum)
|
||||
|
@ -182,7 +185,7 @@ DOMCameraControlListener::OnConfigurationChange(const CameraListenerConfiguratio
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl,
|
||||
Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl,
|
||||
const CameraListenerConfiguration& aConfiguration)
|
||||
: DOMCallback(aDOMCameraControl)
|
||||
, mConfiguration(aConfiguration)
|
||||
|
@ -231,7 +234,7 @@ DOMCameraControlListener::OnAutoFocusMoving(bool aIsMoving)
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl, bool aIsMoving)
|
||||
Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl, bool aIsMoving)
|
||||
: DOMCallback(aDOMCameraControl)
|
||||
, mIsMoving(aIsMoving)
|
||||
{ }
|
||||
|
@ -255,7 +258,7 @@ DOMCameraControlListener::OnFacesDetected(const nsTArray<ICameraControl::Face>&
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl,
|
||||
Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl,
|
||||
const nsTArray<ICameraControl::Face>& aFaces)
|
||||
: DOMCallback(aDOMCameraControl)
|
||||
, mFaces(aFaces)
|
||||
|
@ -280,7 +283,7 @@ DOMCameraControlListener::OnShutter()
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
explicit Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl)
|
||||
explicit Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl)
|
||||
: DOMCallback(aDOMCameraControl)
|
||||
{ }
|
||||
|
||||
|
@ -315,7 +318,7 @@ DOMCameraControlListener::OnAutoFocusComplete(bool aAutoFocusSucceeded)
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl,
|
||||
Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl,
|
||||
bool aAutoFocusSucceeded)
|
||||
: DOMCallback(aDOMCameraControl)
|
||||
, mAutoFocusSucceeded(aAutoFocusSucceeded)
|
||||
|
@ -340,7 +343,7 @@ DOMCameraControlListener::OnTakePictureComplete(uint8_t* aData, uint32_t aLength
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl,
|
||||
Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl,
|
||||
uint8_t* aData, uint32_t aLength, const nsAString& aMimeType)
|
||||
: DOMCallback(aDOMCameraControl)
|
||||
, mData(aData)
|
||||
|
@ -352,7 +355,7 @@ DOMCameraControlListener::OnTakePictureComplete(uint8_t* aData, uint32_t aLength
|
|||
RunCallback(nsDOMCameraControl* aDOMCameraControl) MOZ_OVERRIDE
|
||||
{
|
||||
nsCOMPtr<nsIDOMBlob> picture =
|
||||
File::CreateMemoryFile(mDOMCameraControl,
|
||||
File::CreateMemoryFile(mDOMCameraControl.get(),
|
||||
static_cast<void*>(mData),
|
||||
static_cast<uint64_t>(mLength),
|
||||
mMimeType);
|
||||
|
@ -374,7 +377,7 @@ DOMCameraControlListener::OnUserError(UserContext aContext, nsresult aError)
|
|||
class Callback : public DOMCallback
|
||||
{
|
||||
public:
|
||||
Callback(nsMainThreadPtrHandle<nsDOMCameraControl> aDOMCameraControl,
|
||||
Callback(nsMainThreadPtrHandle<nsISupports> aDOMCameraControl,
|
||||
UserContext aContext,
|
||||
nsresult aError)
|
||||
: DOMCallback(aDOMCameraControl)
|
||||
|
|
|
@ -35,7 +35,7 @@ public:
|
|||
protected:
|
||||
virtual ~DOMCameraControlListener();
|
||||
|
||||
nsMainThreadPtrHandle<nsDOMCameraControl> mDOMCameraControl;
|
||||
nsMainThreadPtrHandle<nsISupports> mDOMCameraControl;
|
||||
CameraPreviewMediaStream* mStream;
|
||||
|
||||
class DOMCallback;
|
||||
|
|
|
@ -342,13 +342,27 @@ nsDOMCameraManager::Register(nsDOMCameraControl* aDOMCameraControl)
|
|||
DOM_CAMERA_LOGI(">>> Register( aDOMCameraControl = %p ) mWindowId = 0x%" PRIx64 "\n", aDOMCameraControl, mWindowId);
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
// Put the camera control into the hash table
|
||||
CameraControls* controls = sActiveWindows->Get(mWindowId);
|
||||
if (!controls) {
|
||||
controls = new CameraControls;
|
||||
controls = new CameraControls();
|
||||
sActiveWindows->Put(mWindowId, controls);
|
||||
}
|
||||
controls->AppendElement(aDOMCameraControl);
|
||||
|
||||
// Remove any stale CameraControl objects to limit our memory usage
|
||||
uint32_t i = controls->Length();
|
||||
while (i > 0) {
|
||||
--i;
|
||||
nsRefPtr<nsDOMCameraControl> cameraControl =
|
||||
do_QueryObject(controls->ElementAt(i));
|
||||
if (!cameraControl) {
|
||||
controls->RemoveElementAt(i);
|
||||
}
|
||||
}
|
||||
|
||||
// Put the camera control into the hash table
|
||||
nsWeakPtr cameraControl =
|
||||
do_GetWeakReference(static_cast<DOMMediaStream*>(aDOMCameraControl));
|
||||
controls->AppendElement(cameraControl);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -362,10 +376,14 @@ nsDOMCameraManager::Shutdown(uint64_t aWindowId)
|
|||
return;
|
||||
}
|
||||
|
||||
uint32_t length = controls->Length();
|
||||
for (uint32_t i = 0; i < length; i++) {
|
||||
nsRefPtr<nsDOMCameraControl> cameraControl = controls->ElementAt(i);
|
||||
cameraControl->Shutdown();
|
||||
uint32_t i = controls->Length();
|
||||
while (i > 0) {
|
||||
--i;
|
||||
nsRefPtr<nsDOMCameraControl> cameraControl =
|
||||
do_QueryObject(controls->ElementAt(i));
|
||||
if (cameraControl) {
|
||||
cameraControl->Shutdown();
|
||||
}
|
||||
}
|
||||
controls->Clear();
|
||||
|
||||
|
|
|
@ -29,7 +29,7 @@ namespace mozilla {
|
|||
}
|
||||
}
|
||||
|
||||
typedef nsTArray<nsRefPtr<mozilla::nsDOMCameraControl> > CameraControls;
|
||||
typedef nsTArray<nsWeakPtr> CameraControls;
|
||||
typedef nsClassHashtable<nsUint64HashKey, CameraControls> WindowTable;
|
||||
|
||||
class nsDOMCameraManager MOZ_FINAL
|
||||
|
|
|
@ -22,7 +22,7 @@ namespace mozilla {
|
|||
class FallbackCameraControl : public CameraControlImpl
|
||||
{
|
||||
public:
|
||||
explicit FallbackCameraControl(uint32_t aCameraId) : CameraControlImpl(aCameraId) { }
|
||||
explicit FallbackCameraControl() : CameraControlImpl() { }
|
||||
|
||||
virtual nsresult Set(uint32_t aKey, const nsAString& aValue) MOZ_OVERRIDE { return NS_ERROR_NOT_IMPLEMENTED; }
|
||||
virtual nsresult Get(uint32_t aKey, nsAString& aValue) MOZ_OVERRIDE { return NS_ERROR_NOT_IMPLEMENTED; }
|
||||
|
|
|
@ -61,7 +61,7 @@ using namespace android;
|
|||
|
||||
// Construct nsGonkCameraControl on the main thread.
|
||||
nsGonkCameraControl::nsGonkCameraControl(uint32_t aCameraId)
|
||||
: CameraControlImpl(aCameraId)
|
||||
: mCameraId(aCameraId)
|
||||
, mLastPictureSize({0, 0})
|
||||
, mLastThumbnailSize({0, 0})
|
||||
, mPreviewFps(30)
|
||||
|
|
|
@ -154,6 +154,8 @@ protected:
|
|||
|
||||
int32_t RationalizeRotation(int32_t aRotation);
|
||||
|
||||
uint32_t mCameraId;
|
||||
|
||||
android::sp<android::GonkCameraHardware> mCameraHw;
|
||||
|
||||
Size mLastPictureSize;
|
||||
|
|
|
@ -251,7 +251,7 @@ public:
|
|||
virtual nsresult StopPreview() = 0;
|
||||
virtual nsresult AutoFocus() = 0;
|
||||
virtual nsresult TakePicture() = 0;
|
||||
virtual nsresult StartRecording(DeviceStorageFileDescriptor *aFileDescriptor,
|
||||
virtual nsresult StartRecording(DeviceStorageFileDescriptor* aFileDescriptor,
|
||||
const StartRecordingOptions* aOptions = nullptr) = 0;
|
||||
virtual nsresult StopRecording() = 0;
|
||||
virtual nsresult StartFaceDetection() = 0;
|
||||
|
@ -293,10 +293,6 @@ public:
|
|||
virtual nsresult GetRecorderProfiles(nsTArray<nsString>& aProfiles) = 0;
|
||||
virtual RecorderProfile* GetProfileInfo(const nsAString& aProfile) = 0;
|
||||
|
||||
virtual uint32_t GetCameraId() = 0;
|
||||
|
||||
virtual void Shutdown() = 0;
|
||||
|
||||
protected:
|
||||
virtual ~ICameraControl() { }
|
||||
|
||||
|
|
|
@ -12,6 +12,8 @@
|
|||
<img src="#" alt="This image is going to load" id="testimage"/>
|
||||
<script class="testbody" type="text/javascript;version=1.7">
|
||||
|
||||
const Cr = Components.results;
|
||||
|
||||
var whichCamera = navigator.mozCameras.getListOfCameras()[0];
|
||||
var config = {
|
||||
mode: 'picture',
|
||||
|
@ -55,15 +57,25 @@ var tests = [
|
|||
{
|
||||
key: "set-picture-size-after-release",
|
||||
func: function testSetPictureSize(camera) {
|
||||
camera.setPictureSize({ width: 0, height: 0 });
|
||||
next();
|
||||
try {
|
||||
camera.setPictureSize({ width: 0, height: 0 });
|
||||
} catch(e) {
|
||||
ok(e.result === SpecialPowers.Cr.NS_ERROR_NOT_AVAILABLE,
|
||||
"setPictureSize() failed with: " + e.name);
|
||||
next();
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
key: "set-thumbnail-size-after-release",
|
||||
func: function testSetThumbnailSize(camera) {
|
||||
camera.setThumbnailSize({ width: 0, height: 0 });
|
||||
next();
|
||||
try {
|
||||
camera.setThumbnailSize({ width: 0, height: 0 });
|
||||
} catch(e) {
|
||||
ok(e.result === SpecialPowers.Cr.NS_ERROR_NOT_AVAILABLE,
|
||||
"setThumbnailSize() failed with: " + e.name);
|
||||
next();
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
|
@ -76,8 +88,13 @@ var tests = [
|
|||
{
|
||||
key: "resume-preview-after-release",
|
||||
func: function testResumePreview(camera) {
|
||||
camera.resumePreview();
|
||||
next();
|
||||
try {
|
||||
camera.resumePreview();
|
||||
} catch(e) {
|
||||
ok(e.result === SpecialPowers.Cr.NS_ERROR_NOT_AVAILABLE,
|
||||
"resumePreview() failed with: " + e.name);
|
||||
next();
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
|
@ -87,7 +104,8 @@ var tests = [
|
|||
ok(false, "autoFocus() succeeded incorrectly");
|
||||
}
|
||||
function onError(error) {
|
||||
ok(error.name === "NS_ERROR_NOT_INITIALIZED", "autoFocus() failed with: " + error);
|
||||
ok(error.name === "NS_ERROR_NOT_AVAILABLE",
|
||||
"autoFocus() failed with: " + error.name);
|
||||
next();
|
||||
}
|
||||
camera.autoFocus().then(onSuccess, onError);
|
||||
|
@ -100,7 +118,8 @@ var tests = [
|
|||
ok(false, "takePicture() succeeded incorrectly");
|
||||
}
|
||||
function onError(error) {
|
||||
ok(error.name === "NS_ERROR_NOT_INITIALIZED", "takePicture() failed with: " + error);
|
||||
ok(error.name === "NS_ERROR_NOT_AVAILABLE",
|
||||
"takePicture() failed with: " + error.name);
|
||||
next();
|
||||
}
|
||||
camera.takePicture(null).then(onSuccess, onError);
|
||||
|
@ -113,7 +132,8 @@ var tests = [
|
|||
ok(false, "startRecording() process succeeded incorrectly");
|
||||
}
|
||||
function onError(error) {
|
||||
ok(error.name === "NS_ERROR_FAILURE", "startRecording() failed with: " + error);
|
||||
ok(error.name === "NS_ERROR_NOT_AVAILABLE",
|
||||
"startRecording() failed with: " + error.name);
|
||||
next();
|
||||
}
|
||||
var recordingOptions = {
|
||||
|
@ -128,8 +148,13 @@ var tests = [
|
|||
{
|
||||
key: "stop-recording-after-release",
|
||||
func: function testStopRecording(camera) {
|
||||
camera.stopRecording();
|
||||
next();
|
||||
try {
|
||||
camera.stopRecording();
|
||||
} catch(e) {
|
||||
ok(e.result === SpecialPowers.Cr.NS_ERROR_NOT_AVAILABLE,
|
||||
"stopRecording() failed with: " + e.name);
|
||||
next();
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
|
@ -139,7 +164,8 @@ var tests = [
|
|||
ok(false, "setConfiguration() process succeeded incorrectly");
|
||||
}
|
||||
function onError(error) {
|
||||
ok(error.name === "NS_ERROR_NOT_INITIALIZED", "setConfiguration() failed with: " + error);
|
||||
ok(error.name === "NS_ERROR_NOT_AVAILABLE",
|
||||
"setConfiguration() failed with: " + error.name);
|
||||
next();
|
||||
}
|
||||
camera.setConfiguration(config).then(onSuccess, onError);
|
||||
|
|
Загрузка…
Ссылка в новой задаче