模式切换控件
CameraControls是相机界面下面的控制栏。
camera_controls.xml中的第一行
布局文件中有一项是
ModuleSwitcher继承自RotateImageView,说明它是一个可旋转的图片,implements
ModuleSwitchListener是模式改变的监听器,这个接口定义在ModuleSwitcher类中,表示它的调用者可以实现这个接口,把自己注册给ModuleSwitcher,当模式改变的时候,可以通知到调用者。
private AnimatorListener mHideAnimationListener;表示这个Listener可以监听动画的消息。而此接口由Animation类实现。
ModuleSwitcher定义了2个构造函数,是因为它的父类定义了2个构造函数,构造函数的参数应该和父类保持一致,且应先调用super()的构造函数。
context就是Activity,context.getResources()就是这个应用的资源,context.getResources().getDimensionPixelSize()就是从资源中获取像素尺寸的值。
mIndicator是个Drawable,可以直接从资源中获取context.getResources().getDrawable(),显示在当前模式的地方。
initializeDrawables()初始化了所有模式的图片,只调用一次。给mDrawIds和mModuleIds 2个全局数组赋值。
onDraw()在绘制时调用,这里绘制了一下mIndicator,Drawable可以直接绘制,不需要通过资源或id,也不需要通过ImageView,先setBounds,再draw就可以了。
initPopup()初始化popup。
getParent(),每个view都可以调用这个函数,来获取自己的parent。
LayoutInflater的作用类似于findViewById,不同的是LayoutInflater用来查找layout文件夹下的布局文件。
LayoutInflater.from(getContext())获取当前应用的布局文件。
LayoutInflater.inflate()是把布局文件实例化成一个View对象,而不是马上显示出来,需要显示的时候,调用SetContentView(View view)显示。
LayoutInflater.from(getContext()).inflate(R.layout.switcher_popup, (ViewGroup) getParent());这句话就是把这个布局文件加入底下控制栏中。
mParent.findViewById(R.id.content);而这个布局文件的控件id为content,所以这句话获取到的是这个xml形成的View。
LayoutParams 是层的参数,层的位置,对齐方式等,每个view都有自己的LayoutParams。
mPopup.getLayoutParams()获取了popup的位置大小等参数。
content.addView,因为content是个LinearLayout,所以可以向里面添加视图。
new LinearLayout.LayoutParams 是新建一个位置尺寸信息。
MeasureSpec封装了父布局对子布局的布局要求,
MeasureSpec.makeMeasureSpec(mParent.getWidth(), MeasureSpec.AT_MOST) 表示最多能达到这个宽度
mPopup.measure(MeasureSpec.makeMeasureSpec(mParent.getWidth(), MeasureSpec.AT_MOST),
这句话的意思是,popup的宽度,最多为父控件的宽度,高度,最多为父控件的高度。
mPopup.getLocationOnScreen(),mPopup.getHeight(),mPopup.getWidth() 获取在屏幕上的坐标,高度,宽度。
mParent.setOnTouchListener(this);就是向父控件注册一个函数,当父控件被触摸时,调用自己的onTouch()函数。onTouch()里就是去关闭popup。
showSwitcher(),显示切换popup。
layoutPopup(),当外界条件改变时,重新设置popup的尺寸,位置等。
mPopup.layout(),设置popup的位置,尺寸。
setTranslationX()设置水平方向的移动距离。
onLayout()在层改变时调用。
设置提示控件 id:on_screen_indicators,配置:menu_indicators.xml
CameraControls.java,是底下控制栏
camera_preferences.xml中存储了所有Camera的设置项。
PreferenceInflater.java是个解析器,用来解析xml中所有的设置项,包括照相机和摄像机的,具体看解析哪个xml文件,保存在自己的成员变量list中,list就是ArrayList类型。
CameraPreference是设置项的基类,是一个抽象类,所有具体的设置项都派生自CameraPreference。
具体的设置项有ListPreference(列表类型),PreferenceGroup(有一些子设置项)
派生自ListPreference的有CountDownTimerPreference
更下层的派生类又有RecordLocationPreference
mContext.getResources().getXml(resId),得到的就是XmlPullParser对象,这个就是该xml文件的解析器。
每种不同类型的CameraPreference检测不同的属性Attr,这些在所有子类的java中处理。
a.recycle()是指a的内容已经使用完,系统可以回收a占用的内存了。
declare-styleable是给自定义组件添加自定义属性用的,自定义组件总有些和平台组件不一样的属性,这时就用到自定义属性了。
例如,CameraPreference是自定义组件,这就为CameraPreference定义了title属性,属性的类型是string。
由于CameraPreference是个抽象类,所有继承自它的子类都可以定义title属性。例如lIstPreference就可以。
TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.CameraPreference, 0, 0);这是在构造函数中,获取这个类的属性,所有这个类支持的属性都放在a中了。
mTitle = a.getString(R.styleable.CameraPreference_title);
R.styleable.CameraPreference_title是由系统生成的,是指所有继承自Camerareference的类的title属性。a.getString()就是获取title属性的值。而每个CameraPreference的子类必须定义title属性,否则就会报错。
PreferenceGroup也是一个控件,它中间可以包含其他的设置项。它本身也是一个设置项。它有一些指向子设置项的指针,可以通过函数访问它的子项。
ListPreference是列表型设置项。
a.getTextArray(R.styleable.ListPreference_entries)是获取entries属性的值,值是字符串array。
entries,entryvalues是写到底层文件中的值,labels。
ListPreference中只存储了value的值,而其他的index,entry,label都是根据value来获取。
可以根据需要去显示entry或label,都是可以显示出来的字符串,没有本质上的区别。在这里,label是大写字母的,显示在圆形菜单里。entry是小写字母,显示在列表菜单里。
ListPreference是负责存储数据的,它决定了显示什么数据,但具体是显示成列表还是圆形菜单,它却不管。所以ListPreference还是数据层面的,不属于ui。
IconListPreference继承自ListPreference,是带图标的列表菜单。
CameraSettings是相机设置项的总的接口,其他模块获取设置项的信息,都可以通过CameraSetings。
getPreferenceGroup()是获取PreferenceGroup,切换模式或切换前后摄像头时调用。
有些设置项是否支持,是根据底层hardware层或profile来获取的,CameraSetting也提供了接口供其他模块调用。CameraSetting在设置项中扮演了Control的角色。
initPreference()是初始化所有的preference,去掉一些不支持的设置项,或一些不支持的设置值。去掉这些之后,剩下的就可以用于界面显示了。
upgradeLocalPreferences(),根据版本号的不同,做略微的调整,保证能够兼容之前的版本。
restorePreferences(),恢复默认设置。
ComboPreferences是用来向文件写入设置的值的,也用来读取。前后摄写的是不同的文件,有些设置项来说,前后摄是一致的,这样的设置项是global,被写入第3个文件。类中类editor提供了修改设置项的接口。
CameraActivity
MyOrientationEventListen
PhotoUI,管理所有照相界面的UI流程,但不负责显示成什么样子。
mTextureView = new TextureView(this);
mTextureView.setSurfaceTextureListene
然后就调用onSurfaceTextureAvailabl
DecodeTask解码任务。
mRenderOverlay用来显示菜单的层,mFlashOverlay显示拍好照之后的动画,mPreviewCover显示预览之前那一帧,mTextureView显示预览图,mOnScreenIndicators显示控制栏的提示图标,mShutterButton拍照按钮,mSwitcher前后摄切换按钮,mCameraControls底下控制栏。
updatePreviewAspectRatio
PieRenderer,继承自OverlayRenderer,是个渲染器。ZoomRenderer也是个渲染器。渲染器最主要就是onDraw函数,在onDraw()里面绘制。
RenderOverlay是个层,可以在它上面进行渲染。
PieItem
PhotoMenu
PieController
PreviewGestures预览手势
CameraControls底下控制栏
FocusOverlayManager对焦管理,所有方式的拍照都要通过这个类。
SurfaceTexture可以从camera获取图像流,但不是马上显示出来。
PhotoController是一套接口,由PhotoModule实现这个接口,PhotoUI调用。
LocationManager位置管理
ModuleSwitcher模式切换选择框
MediaSaveService媒体保存服务
Storage存储相关,把媒体写进媒体库
和底层相关的类:CameraProxy mCameraDevice相机设备。Parameters mParameters相机参数。 CameraInfo info 相机信息。
CameraModule是一套接口,有3个类继承自它。
PhotoModule保存了所有照相模式下的数据,它把所有的Module管理起来。mOnMediaSavedListener监听媒体保存好的消息。MainHandler主线程,处理各种消息。setCameraParametersWhenI
关于预览和显示
TextureView mTextureView;这是用来显示预览的类。
SurfaceTexture mSurfaceTexture;也是和预览相关,但它接受到图像之后,不需要马上显示出来。
mTextureView.setSurfaceTextureListene
mTextureView.addOnLayoutChangeListene
mTextureView.getTransform(mMatrix);设置预览的大小
SurfaceTextureSizeChange
预览改变的消息有:onSurfaceTextureAvailabl
触屏消息传递
PhotoUI创建PreviewGesture。
预览界面点击消息
点击下面控制栏的按钮
全景拍照代码:
WideAnglePanoramaModule Module。onPreviewUIReady UI准备好了。configMosaicPreview 配置预览,停止预览,配置渲染器,并开启预览。MosaicJpeg 全景图片。init 初始化。mOnFrameAvailableRunnabl
WideAnglePanoramaUI 全景UI。
MosaicPreviewRenderer 全景渲染器。
MosaicFrameProcessor 全景进度显示。
MosaicJpeg 全景jpeg图片。