1. 程式人生 > >實現圖片放大縮小,點選熱點響應事件

實現圖片放大縮小,點選熱點響應事件

最近實現一個功能,類似百度地圖。條件:一張圖片。要求圖片可以任意放大縮小移動,點選放縮後圖片的熱點時彈出popwindow,並且給熱點區域新增陰影,顯示出熱點區。
實現思路:
1.先要實現圖片的任意放縮
2.獲得熱點區域的座標
3.點選熱點區域響應事件
4.點選熱點區域彈出popwindows,並指定popwindow的顯示位置
5.給熱點區域新增背景色
解決方法:
1.網上實現圖片任意縮放功能的程式碼有很多,參考的部落格http://yq135314.iteye.com/blog/1997676
2.參考以上部落格,下載了DreameWeaver,獲取熱點座標
3.獲得手指點選時的座標,根據放縮比例得到原座標(放縮前),然後判斷原座標是否在熱點區域。如在響應事件。
4.得到當前手指點選座標,在該座標處新增一個控制元件,比如button,popwindow的位置就相對於button來設定。
5.給當前圖片的熱點區域畫矩形,並儲存為bitmap,然後把這個圖形作為放縮操作的圖形。
遇到問題:
1.點選熱點區域時在該熱點區域彈出popwindow。pop的位置有兩種,相對於某一view位置和絕對位置。在此處需要使用前者,但是熱點區域並沒有view,這就需要動態新增view。判斷點選區域是否是熱點區,若是,則獲取當前座標,並在該點處新增btn,使pop相對btn顯示。
2.給圖片熱點區新增陰影。
 //建立原圖片bitmap,
  (錯誤)
mSourceBitmap = BitmapFactory.decodeStream(hotImgStream);//報異常Immutable bitmap passed to Canvas constructor 不允許直接修改res中的檔案。
  (正確)mSourceBitmap = BitmapFactory.decodeStream(hotImgStream).copy( Bitmap.Config.ARGB_8888, true);
@Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        if (mSourceBitmap != null) {
               Canvas c = new Canvas(mSourceBitmap );
               paint = new Paint();
               paint.setStyle(Paint.Style.FILL);
              paint.setColor(Color.BLACK);
              // 繪製矩形
             canvas.drawRect(10, 10, 100, 100, paint);
            canvas.drawBitmap(mSourceBitmap, mMatrix, null);
        } else {
            LogUtils.d(TAG, "mBlockBitmap is null !");
        }
    }
//執行結果:一張空白圖片,因為新建的一張畫布,雖然
Canvas c = new Canvas(mSourceBitmap );但沒有對畫布儲存,所以顯示一張空白畫布。正確步驟如下:
  mSourceBitmap = BitmapFactory.decodeStream(hotImgStream).copy(  Bitmap.Config.ARGB_8888, true);
@Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        if (mSourceBitmap != null) {
            mBlockBitmap = Bitmap.createBitmap(mSourceBitmap.getWidth(), mSourceBitmap.getHeight(), Bitmap.Config.ARGB_8888);//建立一個bitmap

            Canvas c = new Canvas(mBlockBitmap);//建立一個新畫布
            c.drawBitmap(mSourceBitmap, 0, 0, null);//畫上背景
            paint = new Paint();
           //這樣寫畫出的矩形是實心的不透明的,setRGB就可以顯示成功,不知道為什麼
            // paint.setAlpha(1);
            // paint.setColor(Color.BLUE);
            paint.setARGB(50, 128, 138, 135);
            pt = new int[mHotAreas.size()][4];
            pt = getLocat(mHotAreas);
            for (int i = 0; i < mHotAreas.size(); i++) {
                c.drawRect(pt[i][0], pt[i][1], pt[i][2], pt[i][3], paint);//畫矩形
            }
            c.save(Canvas.ALL_SAVE_FLAG);//儲存畫布
            canvas.drawBitmap(mBlockBitmap, mMatrix, null);//顯示帶熱點陰影的圖
        } else {
            LogUtils.d(TAG, "mBlockBitmap is null !");
        }
    }
效果圖:

心得:最近一直在告誡自己,進度慢不要緊,重要的是想清楚,思路清晰。就像我在畫熱點陰影的時候,思路想通了,覺得邏輯上行得通,可是畫出的是一張空白,不知道這個空白畫布是哪來的,折騰了好久,才發現原來是見了一張空白畫布。做任何事,先有個清晰的思路,然後在跟著思路一步步走下去,即時後來出錯了,也能大概判斷錯在哪裡,這樣比盲目效仿效率更高!敲程式碼如此,做人做事也一樣!