Android不規(guī)則圖像填充顏色小游戲
一、概述
近期群里偶然看到一哥們?cè)谌豪锪牟灰?guī)則圖像填充什么四聯(lián)通、八聯(lián)通什么的,就本身好學(xué)務(wù)實(shí)的態(tài)度去查閱了相關(guān)資料。對(duì)于這類著色的資料,最好的就是去搜索些相關(guān)app,根據(jù)我的觀察呢,不規(guī)則圖像填充在著色游戲里面應(yīng)用居多,不過大致可以分為兩種:
基于層的的填充
基于邊界的填充
那么針對(duì)上述兩種,我們會(huì)通過兩篇博文來講解,本篇就是敘述基于層的填充方式,那么什么基于層的填充方式呢?其實(shí)就是一張圖實(shí)際上是由多個(gè)層組成的,每個(gè)層顯示部分圖像(無圖像部分為透明),多層疊加后形成一張完整的圖案,圖層間是疊加的關(guān)系,類似下圖。

相信大家如果學(xué)過PS,對(duì)上述肯定再了解不過了。比如你要繪制一個(gè)天空,你可以最底層去繪制藍(lán)天,在上層繪制白云,再上層會(huì)執(zhí)行小鳥。然后三層疊加以后就是一副小鳥在天空翱翔的圖了。
二、效果與分析
好了,接下來看下今天的效果。

ok,可以看到一個(gè)簡單的著色效果,其實(shí)原理很簡單,首先呢,該圖實(shí)際上是由7層組成:
例如下圖。

那么如果我們需要給這幅圖的某個(gè)位置著色,實(shí)際上是給某一層的非透明區(qū)域著色。實(shí)際上就轉(zhuǎn)化為:
用戶點(diǎn)擊的(x,y)-> 判斷落在哪一層的非透明區(qū)域 -> 然后給該層非透明區(qū)域著色。
ok,這樣原理就敘述清楚了,實(shí)際上也是非常的簡單,基于該原理,我們可以自定義一個(gè)View,然后一幅一幅去繪制圖層,最后按照上述步驟去編寫代碼。不過,我們還有可以偷懶的地方,其實(shí)沒必要我們自己去一個(gè)圖層一個(gè)圖層的繪制,我們可以利用Drawable去完成圖層疊加的工作,我們有一類Drawable叫做LayerDrawable,對(duì)應(yīng)的xml為layer-list,我們可以通過使用LayerDrawable極大的簡化我們的工作。
三、編碼與實(shí)現(xiàn)
上述已經(jīng)描述很清楚了,我再給大家細(xì)化一下:
1.layer-list中去定義我們的drawable;
2.然后把該drawable作為我們View的背景;
3.復(fù)寫onTouchEvent方法;
4.判斷用戶點(diǎn)擊的坐標(biāo)落在哪一層的非透明位置,改變?cè)搶臃峭该鲄^(qū)域顏色。
(一)layer-list
<?xml version="1.0" encoding="utf-8"?> <layer-list xmlns:android="http://schemas.android.com/apk/res/android"> <item android:drawable="@drawable/eel_mask1"/> <item android:drawable="@drawable/eel_mask2"/> <item android:drawable="@drawable/eel_mask3"/> <item android:drawable="@drawable/eel_mask4"/> <item android:drawable="@drawable/eel_mask5"/> <item android:drawable="@drawable/eel_mask6"/> <item android:drawable="@drawable/eel_mask7"/> </layer-list>
ok,這樣我們的drawable就ok了~~沒撒說的,不過layer-list可以做很多事情,大家可以關(guān)注下。
(二)View代碼
package com.zhy.colour_app_01;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Color;
import android.graphics.PorterDuff;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.graphics.drawable.LayerDrawable;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
import java.util.Random;
/**
* Created by zhy on 15/5/14.
*/
public class ColourImageBaseLayerView extends View
{
private LayerDrawable mDrawables;
public ColourImageBaseLayerView(Context context, AttributeSet attrs)
{
super(context, attrs);
mDrawables = (LayerDrawable) getBackground();
}
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec)
{
setMeasuredDimension(mDrawables.getIntrinsicWidth(), mDrawables.getIntrinsicHeight());
}
@Override
public boolean onTouchEvent(MotionEvent event)
{
final float x = event.getX();
final float y = event.getY();
if (event.getAction() == MotionEvent.ACTION_DOWN)
{
Drawable drawable = findDrawable(x, y);
if (drawable != null)
drawable.setColorFilter(randomColor(), PorterDuff.Mode.SRC_IN);
}
return super.onTouchEvent(event);
}
private int randomColor()
{
Random random = new Random();
int color = Color.argb(255, random.nextInt(256), random.nextInt(256), random.nextInt(256));
return color;
}
private Drawable findDrawable(float x, float y)
{
final int numberOfLayers = mDrawables.getNumberOfLayers();
Drawable drawable = null;
Bitmap bitmap = null;
for (int i = numberOfLayers - 1; i >= 0; i--)
{
drawable = mDrawables.getDrawable(i);
bitmap = ((BitmapDrawable) drawable).getBitmap();
try
{
int pixel = bitmap.getPixel((int) x, (int) y);
if (pixel == Color.TRANSPARENT)
{
continue;
}
} catch (Exception e)
{
continue;
}
return drawable;
}
return null;
}
}
ok,代碼也比較簡單,首先我們把drawable作為view的背景,然后在構(gòu)造中獲取drawable(LayerDrawable)。接下來復(fù)寫onTouchEvent,捕獲用戶點(diǎn)擊的(x,y),根據(jù)(x,y)去找出當(dāng)前點(diǎn)擊的是哪一層(必須點(diǎn)擊在非透明區(qū)域),最后通過設(shè)置setColorFilter去改變顏色即可~很easy吧最后貼下布局文件:
(三)布局文件
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
android:paddingBottom="@dimen/activity_vertical_margin"
tools:context=".MainActivity">
<com.zhy.colour_app_01.ColourImageBaseLayerView
android:background="@drawable/eel"
android:layout_width="match_parent"
android:layout_centerInParent="true"
android:layout_height="match_parent"/>
</RelativeLayout>
以上就是這篇文章的全部內(nèi)容了,希望本文的內(nèi)容對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,如果有疑問大家可以留言交流,謝謝大家對(duì)腳本之家的支持。
- Android Studio使用小技巧:布局預(yù)覽時(shí)填充數(shù)據(jù)
- 基于Android中的 AutoCompleteTextView實(shí)現(xiàn)自動(dòng)填充
- Android矢量圖之VectorDrawable類自由填充色彩
- Android ListView填充數(shù)據(jù)的方法
- Android ScrollView無法填充滿屏幕的解決辦法
- Android圖片等比例縮放和填充屏幕效果
- Android圖像處理之泛洪填充算法
- Android多邊形區(qū)域遞歸種子填充算法的示例代碼
- Android不規(guī)則封閉區(qū)域填充色彩的實(shí)例代碼
- Android多邊形區(qū)域掃描線種子填充算法的示例
相關(guān)文章
Android中顏色選擇器和改變字體顏色的實(shí)例教程
這篇文章主要介紹了Android中顏色選擇器和改變字體顏色的實(shí)例教程,其中改變字體顏色用到了ColorPicker顏色選擇器,需要的朋友可以參考下2016-04-04
Android開發(fā)之利用Activity實(shí)現(xiàn)Dialog對(duì)話框
這篇文章主要給大家介紹了Android開發(fā)之如何利用Activity實(shí)現(xiàn)Dialog對(duì)話框效果,文中給出了詳細(xì)的示例代碼,相信對(duì)大家的理解及學(xué)習(xí)具有一定的參考借鑒價(jià)值,有需要的朋友們下面來一起看看吧。2016-12-12
Android提高之Android手機(jī)與BLE終端通信
這篇文章主要介紹了Android手機(jī)與BLE終端通信的方法,有很大的實(shí)用價(jià)值,需要的朋友可以參考下2014-08-08
Android App中的GridView網(wǎng)格布局使用指南
GridView布局所實(shí)現(xiàn)的就是類似于九宮格的矩陣界面效果,下面整理了Android App中的GridView網(wǎng)格布局使用指南,包括分割線的添加與自定義GridView的實(shí)現(xiàn)等技巧,需要的朋友可以參考下2016-06-06

