Android回顧--(三十) 手勢(shì)和自定義ViewGroup

手勢(shì)

是手指在屏幕上的一切操作辜妓,包括單擊矾克、雙擊、長按捏鱼、滑動(dòng)执庐、滾動(dòng)等。

使用方式

  1. 聲明一個(gè)GestureDetector對(duì)象

GestureDetector mGestureDetector=null;//聲明成全局變量

  1. 實(shí)例化手勢(shì)對(duì)象穷躁,并且實(shí)現(xiàn)手勢(shì)的監(jiān)聽OnGestureListener

mGestureDetector=new GestureDetector(MainActivity.this,new MyOnGestureListener());

  1. 創(chuàng)建一個(gè)類實(shí)現(xiàn)GestureDetector.OnGestureListener耕肩,并重寫里面的6個(gè)方法:

private class MyOnGestureListener implements GestureDetector.OnGestureListener

  • onDown:手指按下的監(jiān)聽
    /**
     * 手指按下的時(shí)候的監(jiān)聽
     */
    @Override
    public boolean onDown(MotionEvent e) {
        Log.e("----------------","onDown");
        return false;
    }
  • onShowPress:手指短按的監(jiān)聽
/**
 * 手指按住不放那么都會(huì)觸發(fā)這個(gè)函數(shù)
 */
@Override
public void onShowPress(MotionEvent e) {
    Log.e("----------------","onShowPress");
}
  • onSingleTapUp:單擊
/**
 * 單擊
 */
@Override
public boolean onSingleTapUp(MotionEvent e) {
    Log.e("----------------","onSingleTapUp");
    return false;
}
  • onScroll:滾動(dòng)
        /**
         * 滾動(dòng)
         * @param e1:表示的是上一次的開始的時(shí)候的事件
         * @param e2 :這一次的時(shí)候的事件
         * @param distanceX:在x軸上滾動(dòng)的距離  從左邊往右邊滾動(dòng)那么這個(gè)值是負(fù)值 / 在x軸上從右邊往左邊滾動(dòng)的話那么這個(gè)值是正值
         * @param distanceY:在y軸上滾動(dòng)的距離 從上--->下  負(fù)值  從下--->上 正值
         * @return
         */
        @Override
        public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
            Log.e("----------------","onScroll");
//            Log.e("------distansX----",distanceX+"-----");
//            Log.e("------distansY----",distanceY+"-----");
            int startX= (int) e1.getX();
            int endX= (int) e2.getX();
            int startY= (int) e1.getY();
            int endY= (int) e2.getY();
            if(Math.abs(startX-endX)>Math.abs(startY-endY)){    //默認(rèn)就是左右的滑動(dòng)
                if(startX>endX){   //從右邊往左邊來進(jìn)行滑動(dòng)
                    Log.e("-----------","從右邊往左邊滑動(dòng)");
                }else{   //從左邊往右邊進(jìn)行滑動(dòng)
                    Log.e("-----------","從左邊往右邊滑動(dòng)");
                }
            }else{
                if(endY>startY){   //從上邊往下邊來進(jìn)行滑動(dòng)
                    Log.e ("-----------","從上邊往下邊滑動(dòng)");
                }else{   //從左邊往右邊進(jìn)行滑動(dòng)
                    Log.e ("-----------","從下邊往上邊滑動(dòng)");
                }
            }
            return false;
        }
  • onLongPress:長按,和onSowPress是時(shí)間上的區(qū)別。
/**
 * 長按    和上面那個(gè)onShowPress的區(qū)別是時(shí)間上的區(qū)別问潭,也就是說如果觸發(fā)了 onLongPress就一定要觸發(fā)onShowPress
 */
@Override
public void onLongPress(MotionEvent e) {
    Log.e("----------------","onLongPress");
}
  • onFlinf:滑動(dòng),滑動(dòng)和滾動(dòng)的區(qū)別:滑動(dòng)是在屏幕上面快速的移動(dòng)一段距離婚被,有滑動(dòng)一定有滾動(dòng)狡忙,有滾動(dòng)不一樣有滑動(dòng)。
/**
 * 滑動(dòng)      滑動(dòng)和滾動(dòng)的區(qū)別
 *   滑動(dòng)是在屏幕上快速的移動(dòng)一段距離
 *   滾動(dòng):是在屏幕上慢慢的移動(dòng)一段距離
 *   有滑動(dòng)就一定有滾動(dòng)
 *   有滾動(dòng)不一定有滑動(dòng)
 * @param e1:上一次的那個(gè)開始的事件
 * @param e2:上一次結(jié)束的事件
 * @param velocityX:表示的是單位時(shí)間內(nèi)在x軸上移動(dòng)的distance
 * @param velocityY:表示單位事件內(nèi)在Y軸上移動(dòng)的距離   這個(gè)主要用來判定那個(gè)到底是往哪里滑動(dòng)
 * @return
 */
@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
    Log.e("----------------","onFling");
    return false;
}
  1. 將當(dāng)前觸摸區(qū)域的事件傳遞給手勢(shì)來進(jìn)行處理址芯。

例如:重寫onToucheEvent方法灾茁,將觸摸事件返回給手勢(shì)去處理

@Override
public boolean onTouchEvent(MotionEvent event) {
    return mGestureDetector.onTouchEvent(event);
}

ViewGroup的用法:

ViewGroup:容器,在ViewGroup里面轉(zhuǎn)的是View,或者新的ViewGroup谷炸。ViewGroup可以看做是所有容器的父類北专。

ViewGroup和View的關(guān)系和區(qū)別?
??View是所有控件和容器的最大的父類旬陡,ViewGroup是繼承于View的拓颓,View也是ViewGroup的父類,在開發(fā)中如果要將View和容器區(qū)分開的話描孟,可以認(rèn)為ViewGroup就是所有容器的父類驶睦。

學(xué)習(xí)ViewGroup的作用:
  1. 可以自定義布局-->流式布局
  2. 可以自定義容器-->自己決定容器能夠裝多少數(shù)據(jù)砰左,容器中的控件位置也是自己決定

自定義ViewGroup的步驟:

  1. 編寫一個(gè)類繼承于ViewGroup,并且重寫有兩個(gè)參數(shù)的構(gòu)造函數(shù)
  2. 重寫ViewGroup里面的onLayout方法场航。

/**
 * 確定那個(gè)兒子的位置
 * @param changed
 * @param l:兒子的左邊頂部的x的坐標(biāo)
 * @param t:兒子左邊頂部的y坐標(biāo)
 * @param r:兒子右邊底部的x的坐標(biāo)
 * @param b:兒子的右邊的底部的y坐標(biāo)
 */
@Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
  //在ViewGroup中獲取那個(gè)兒子的數(shù)量
    int childCount = getChildCount();
  //給孩子設(shè)置那個(gè)顯示的位置
    //得到這個(gè)孩子
    View childView=getChildAt(0);
    //給兒子設(shè)置個(gè)位置
 /*   Log.e("---------",childView.getMeasuredWidth()+"");
    Log.e("---------",childView.getMeasuredHeight()+"");*/
    childView.layout(100,100,childView.getMeasuredWidth()+100,childView.getMeasuredHeight()+100);
}
  1. 重寫ViewGroup中的onMeasure方法
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
    super.onMeasure(widthMeasureSpec, heightMeasureSpec);
    //測(cè)量兒子的第一種模式:交給他爹來測(cè)咋們不用管缠导,一般情況下都用這種方法
    //怎么交給他爹測(cè)
    //這句話一旦調(diào)用的話那么他的孩子就有那個(gè)寬高了...
    //優(yōu)點(diǎn):方便而且不用謝很多的代碼  孩子的高度就有了....
    measureChild(getChildAt(0),widthMeasureSpec,heightMeasureSpec);
    //還有第二種測(cè)量模式:這種測(cè)量模式就是:自己編寫代碼來進(jìn)行測(cè)量,較復(fù)雜
    //自己測(cè)  獲取測(cè)量模式
    int count=getChildCount();
    Log.e("------孩子的個(gè)數(shù)---",count+"");
   if(tag){
        tag=false;
        int widthMode=MeasureSpec.getMode(widthMeasureSpec);
        int heightMode=MeasureSpec.getMode(heightMeasureSpec);
        //獲取那個(gè)建議的寬和高
        int widthSize=MeasureSpec.getSize(widthMeasureSpec);
        int heightSize=MeasureSpec.getSize(heightMeasureSpec);
        //第三步就來確定那個(gè)是使用的具體的值還是那個(gè)wrap_content
        //表示的是最終算出來的那個(gè)寬和高
        int describleWidth=200;
        int describleHeight=200;
        int width=0;
        int height=0;
        if(widthMode==MeasureSpec.AT_MOST){ //這個(gè)情況表示的是那個(gè)wrap_content
            width=Math.min(widthSize,describleWidth);
        }else if(widthMode==MeasureSpec.EXACTLY){  //這個(gè)表示的是精確的值或者是match_parent
            width=widthSize;
        }
        //玩的是那個(gè)高的測(cè)量模式
        if(heightMode==MeasureSpec.AT_MOST){   //這個(gè)表示的是wrap_content
            height=Math.min(describleHeight,heightSize);
        }else if(heightMode==MeasureSpec.EXACTLY){  //表示的是那個(gè)實(shí)際的值或者是那個(gè)充滿容器
            height=heightSize;
        }
        Log.e("----------------",width+" 之中");
        Log.e("------------hei----",height+" 之中");
        //下面就將咋們的測(cè)量的結(jié)果傳遞給那個(gè)給兒子測(cè)量的方法     getChildAt(0).measure(MeasureSpec.makeMeasureSpec(width,widthMode),MeasureSpec.makeMeasureSpec(height,heightMode));
    }

注意:在ViewGroup中只能使用getMeasuredWidth和getMeasuredHeight來測(cè)量寬和高溉痢。

  1. 在需要使用該ViewGroup的布局文件聲明控件
<com.fox.ViewGroupDemo.MyViewGroup
    android:layout_width="400dp"
    android:layout_height="300dp"
    android:background="#f07">
    <Button
        android:layout_width="100dp"
        android:layout_height="50dp"
        android:text="按鈕"/>
</com.fox.ViewGroupDemo.MyViewGroup>
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末僻造,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子孩饼,更是在濱河造成了極大的恐慌髓削,老刑警劉巖,帶你破解...
    沈念sama閱讀 217,509評(píng)論 6 504
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件捣辆,死亡現(xiàn)場(chǎng)離奇詭異蔬螟,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)汽畴,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,806評(píng)論 3 394
  • 文/潘曉璐 我一進(jìn)店門旧巾,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人忍些,你說我怎么就攤上這事鲁猩。” “怎么了罢坝?”我有些...
    開封第一講書人閱讀 163,875評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵廓握,是天一觀的道長。 經(jīng)常有香客問我嘁酿,道長隙券,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,441評(píng)論 1 293
  • 正文 為了忘掉前任闹司,我火速辦了婚禮娱仔,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘游桩。我一直安慰自己牲迫,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,488評(píng)論 6 392
  • 文/花漫 我一把揭開白布借卧。 她就那樣靜靜地躺著盹憎,像睡著了一般。 火紅的嫁衣襯著肌膚如雪铐刘。 梳的紋絲不亂的頭發(fā)上陪每,一...
    開封第一講書人閱讀 51,365評(píng)論 1 302
  • 那天,我揣著相機(jī)與錄音,去河邊找鬼奶稠。 笑死俯艰,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的锌订。 我是一名探鬼主播竹握,決...
    沈念sama閱讀 40,190評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼辆飘!你這毒婦竟也來了啦辐?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,062評(píng)論 0 276
  • 序言:老撾萬榮一對(duì)情侶失蹤蜈项,失蹤者是張志新(化名)和其女友劉穎芹关,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體紧卒,經(jīng)...
    沈念sama閱讀 45,500評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡侥衬,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,706評(píng)論 3 335
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了跑芳。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片轴总。...
    茶點(diǎn)故事閱讀 39,834評(píng)論 1 347
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖博个,靈堂內(nèi)的尸體忽然破棺而出怀樟,到底是詐尸還是另有隱情,我是刑警寧澤盆佣,帶...
    沈念sama閱讀 35,559評(píng)論 5 345
  • 正文 年R本政府宣布往堡,位于F島的核電站,受9級(jí)特大地震影響共耍,放射性物質(zhì)發(fā)生泄漏虑灰。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,167評(píng)論 3 328
  • 文/蒙蒙 一痹兜、第九天 我趴在偏房一處隱蔽的房頂上張望瘩缆。 院中可真熱鬧,春花似錦佃蚜、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,779評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至归露,卻和暖如春洲脂,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,912評(píng)論 1 269
  • 我被黑心中介騙來泰國打工恐锦, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留往果,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 47,958評(píng)論 2 370
  • 正文 我出身青樓一铅,卻偏偏與公主長得像陕贮,于是被迫代替她去往敵國和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子潘飘,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,779評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容