/* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this file, * You can obtain one at http://mozilla.org/MPL/2.0/. */ #ifndef DOM_CAMERA_DOMCAMERACONTROL_H #define DOM_CAMERA_DOMCAMERACONTROL_H #include "nsCOMPtr.h" #include "nsAutoPtr.h" #include "nsCycleCollectionParticipant.h" #include "mozilla/dom/CameraControlBinding.h" #include "ICameraControl.h" #include "CameraCommon.h" #include "DOMMediaStream.h" #include "AudioChannelAgent.h" #include "nsProxyRelease.h" #include "nsHashPropertyBag.h" #include "DeviceStorage.h" #include "DOMCameraControlListener.h" class nsDOMDeviceStorage; class nsPIDOMWindow; class nsIDOMBlob; namespace mozilla { namespace dom { class CameraCapabilities; class CameraPictureOptions; class CameraStartRecordingOptions; template class Optional; } class ErrorResult; class StartRecordingHelper; // Main camera control. class nsDOMCameraControl MOZ_FINAL : public DOMMediaStream { public: NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsDOMCameraControl, DOMMediaStream) NS_DECL_ISUPPORTS_INHERITED // Because this header's filename doesn't match its C++ or DOM-facing // classname, we can't rely on the [Func="..."] WebIDL tag to implicitly // include the right header for us; instead we must explicitly include a // HasSupport() method in each header. We can get rid of these with the // Great Renaming proposed in bug 983177. static bool HasSupport(JSContext* aCx, JSObject* aGlobal); nsDOMCameraControl(uint32_t aCameraId, const dom::CameraConfiguration& aInitialConfig, dom::GetCameraCallback* aOnSuccess, dom::CameraErrorCallback* aOnError, nsPIDOMWindow* aWindow); void Shutdown(); nsPIDOMWindow* GetParentObject() const { return mWindow; } // Attributes. void GetEffect(nsString& aEffect, ErrorResult& aRv); void SetEffect(const nsAString& aEffect, ErrorResult& aRv); void GetWhiteBalanceMode(nsString& aMode, ErrorResult& aRv); void SetWhiteBalanceMode(const nsAString& aMode, ErrorResult& aRv); void GetSceneMode(nsString& aMode, ErrorResult& aRv); void SetSceneMode(const nsAString& aMode, ErrorResult& aRv); void GetFlashMode(nsString& aMode, ErrorResult& aRv); void SetFlashMode(const nsAString& aMode, ErrorResult& aRv); void GetFocusMode(nsString& aMode, ErrorResult& aRv); void SetFocusMode(const nsAString& aMode, ErrorResult& aRv); double GetZoom(ErrorResult& aRv); void SetZoom(double aZoom, ErrorResult& aRv); JS::Value GetMeteringAreas(JSContext* aCx, ErrorResult& aRv); void SetMeteringAreas(JSContext* aCx, JS::Handle aAreas, ErrorResult& aRv); JS::Value GetFocusAreas(JSContext* aCx, ErrorResult& aRv); void SetFocusAreas(JSContext* aCx, JS::Handle aAreas, ErrorResult& aRv); JS::Value GetPictureSize(JSContext* aCx, ErrorResult& aRv); void SetPictureSize(JSContext* aCx, JS::Handle aSize, ErrorResult& aRv); JS::Value GetThumbnailSize(JSContext* aCx, ErrorResult& aRv); void SetThumbnailSize(JSContext* aCx, JS::Handle aSize, ErrorResult& aRv); double GetFocalLength(ErrorResult& aRv); double GetFocusDistanceNear(ErrorResult& aRv); double GetFocusDistanceOptimum(ErrorResult& aRv); double GetFocusDistanceFar(ErrorResult& aRv); void SetExposureCompensation(const dom::Optional& aCompensation, ErrorResult& aRv); double GetExposureCompensation(ErrorResult& aRv); int32_t SensorAngle(); already_AddRefed Capabilities(); void GetIsoMode(nsString& aMode, ErrorResult& aRv); void SetIsoMode(const nsAString& aMode, ErrorResult& aRv); // Unsolicited event handlers. dom::CameraShutterCallback* GetOnShutter(); void SetOnShutter(dom::CameraShutterCallback* aCb); dom::CameraClosedCallback* GetOnClosed(); void SetOnClosed(dom::CameraClosedCallback* aCb); dom::CameraRecorderStateChange* GetOnRecorderStateChange(); void SetOnRecorderStateChange(dom::CameraRecorderStateChange* aCb); dom::CameraPreviewStateChange* GetOnPreviewStateChange(); void SetOnPreviewStateChange(dom::CameraPreviewStateChange* aCb); dom::CameraAutoFocusMovingCallback* GetOnAutoFocusMoving(); void SetOnAutoFocusMoving(dom::CameraAutoFocusMovingCallback* aCb); dom::CameraFaceDetectionCallback* GetOnFacesDetected(); void SetOnFacesDetected(dom::CameraFaceDetectionCallback* aCb); // Methods. void SetConfiguration(const dom::CameraConfiguration& aConfiguration, const dom::Optional >& aOnSuccess, const dom::Optional >& aOnError, ErrorResult& aRv); void AutoFocus(dom::CameraAutoFocusCallback& aOnSuccess, const dom::Optional >& aOnError, ErrorResult& aRv); void StartFaceDetection(ErrorResult& aRv); void StopFaceDetection(ErrorResult& aRv); void TakePicture(const dom::CameraPictureOptions& aOptions, dom::CameraTakePictureCallback& aOnSuccess, const dom::Optional >& aOnError, ErrorResult& aRv); void StartRecording(const dom::CameraStartRecordingOptions& aOptions, nsDOMDeviceStorage& storageArea, const nsAString& filename, dom::CameraStartRecordingCallback& aOnSuccess, const dom::Optional >& aOnError, ErrorResult& aRv); void StopRecording(ErrorResult& aRv); void ResumePreview(ErrorResult& aRv); void ReleaseHardware(const dom::Optional >& aOnSuccess, const dom::Optional >& aOnError, ErrorResult& aRv); void ResumeContinuousFocus(ErrorResult& aRv); virtual JSObject* WrapObject(JSContext* aCx) MOZ_OVERRIDE; protected: virtual ~nsDOMCameraControl(); class DOMCameraConfiguration MOZ_FINAL : public dom::CameraConfiguration { public: NS_INLINE_DECL_REFCOUNTING(DOMCameraConfiguration) DOMCameraConfiguration(); DOMCameraConfiguration(const dom::CameraConfiguration& aConfiguration); // Additional configuration options that aren't exposed to the DOM uint32_t mMaxFocusAreas; uint32_t mMaxMeteringAreas; private: // Private destructor, to discourage deletion outside of Release(): ~DOMCameraConfiguration(); }; friend class DOMCameraControlListener; friend class mozilla::StartRecordingHelper; void OnCreatedFileDescriptor(bool aSucceeded); void OnAutoFocusComplete(bool aAutoFocusSucceeded); void OnAutoFocusMoving(bool aIsMoving); void OnTakePictureComplete(nsIDOMBlob* aPicture); void OnFacesDetected(const nsTArray& aFaces); void OnHardwareStateChange(DOMCameraControlListener::HardwareState aState); void OnPreviewStateChange(DOMCameraControlListener::PreviewState aState); void OnRecorderStateChange(CameraControlListener::RecorderState aState, int32_t aStatus, int32_t aTrackNum); void OnConfigurationChange(DOMCameraConfiguration* aConfiguration); void OnShutter(); void OnError(CameraControlListener::CameraErrorContext aContext, const nsAString& mError); bool IsWindowStillActive(); nsresult NotifyRecordingStatusChange(const nsString& aMsg); nsRefPtr mCameraControl; // non-DOM camera control // An agent used to join audio channel service. nsCOMPtr mAudioChannelAgent; nsresult Set(JSContext* aCx, uint32_t aKey, const JS::Value& aValue, uint32_t aLimit); nsresult Get(JSContext* aCx, uint32_t aKey, JS::Value* aValue); nsRefPtr mCurrentConfiguration; nsRefPtr mCapabilities; // solicited camera control event handlers nsRefPtr mGetCameraOnSuccessCb; nsRefPtr mGetCameraOnErrorCb; nsRefPtr mAutoFocusOnSuccessCb; nsRefPtr mAutoFocusOnErrorCb; nsRefPtr mTakePictureOnSuccessCb; nsRefPtr mTakePictureOnErrorCb; nsRefPtr mStartRecordingOnSuccessCb; nsRefPtr mStartRecordingOnErrorCb; nsRefPtr mReleaseOnSuccessCb; nsRefPtr mReleaseOnErrorCb; nsRefPtr mSetConfigurationOnSuccessCb; nsRefPtr mSetConfigurationOnErrorCb; // unsolicited event handlers nsRefPtr mOnShutterCb; nsRefPtr mOnClosedCb; nsRefPtr mOnRecorderStateChangeCb; nsRefPtr mOnPreviewStateChangeCb; nsRefPtr mOnAutoFocusMovingCb; nsRefPtr mOnFacesDetectedCb; // Camera event listener; we only need this weak reference so that // we can remove the listener from the camera when we're done // with it. DOMCameraControlListener* mListener; // our viewfinder stream CameraPreviewMediaStream* mInput; // set once when this object is created nsCOMPtr mWindow; dom::CameraStartRecordingOptions mOptions; nsRefPtr mDSFileDescriptor; private: nsDOMCameraControl(const nsDOMCameraControl&) MOZ_DELETE; nsDOMCameraControl& operator=(const nsDOMCameraControl&) MOZ_DELETE; }; } // namespace mozilla #endif // DOM_CAMERA_DOMCAMERACONTROL_H