首先我需要這樣一個介面
這個介面是在使用AudioManager.adjustStreamVolume(int streamType, int direction, int flags)顯示出來的,記住flags這裡傳 AudioManager.FLAG_SHOW_UI才會顯示
不然只是邏輯上調整了某個流的聲音,使用者他看不到介面不知道成功與否。
然後我有一個功能介面是和這個一樣的,但功能不一樣,好吧,我知道android內建的介面並不好看,但這裡只是說明原理和方法,美觀不予討論。
這裡核心的2個組件就是一個TextView和ProgressBar。如果自訂的話,需要寫一個layout來包裹這2個組件 然後當點擊一個按鈕時顯示出來。
讓我們在回到android內建的介面中,當他點擊一個按鈕時,他會彈出來並且隔一會就會自動消失。這個自動消失我覺得很有用,因為使用者只需要調整那一會
能看到介面的改變就行了,不需要一直顯示,不然還要讓使用者在點個返回?多麼麻煩呢,操作簡單才是重要的。
於是我想到了android 內建的toast有這個功能。好的!大方向確定了,就開始寫代碼吧
邏輯是這樣的讓使用者點擊某個按鈕時,彈出上面那個介面,然後過一會消失,這裡在顯示toast的時候還需要調用改變進度條進度的方法。
接下來上代碼吧:
// ////////////////////////先產生一個toast和progress介面
pb = new ProgressBar(context, null,
android.R.attr.progressBarStyleHorizontal);
pb.setMax(GameConfig.GameSpeedMax);
pb.setProgress(GameConfig.GameSpeedDefault);
pb.setLayoutParams(new LinearLayout.LayoutParams(
ExtensionLayoutConfig.ProgressBarWidth,
LinearLayout.LayoutParams.WRAP_CONTENT));
toast = Toast.makeText(context,
RFileIDConvert.getString("gameSpeedBarTitle"),
Toast.LENGTH_LONG);
toast.setGravity(Gravity.TOP, 0, 0);
LinearLayout toastView = (LinearLayout) toast.getView();
toastView.setGravity(Gravity.CENTER);
//請注意這裡傳1是必要的,因為他的textView已經在建立的時候添加進去了,如果你傳0
//那麼上面會先顯示進度條 下面再顯示文字,如果你需要的話可以這麼做,但我現在需要
//文字在上方 進度條在下面 so 傳1
toastView.addView(pb, 1);
下面是給外部調用的2個介面:
/**
* 設定進度
*/
public void setGameSpeedBarProgress(int progress) {
pb.setProgress(progress);
}
/**
* 顯示toast
*/
public void gameSpeedBarShow() {
toast.show();
}
出來的效果是這樣
發現和原來的相比沒那麼大氣,所以還需要調整下間距,這個簡單 我明天再完善它, 大概功能就是這樣了。
總結。大家請不要小看這麼一個介面,我剛開始也覺得很容易,可實現起來發現的問題也不少。
1.一般布局我習慣用代碼布局,但碰到ProgressBar我只能無語。在代碼中預設的風格是環形的,在XML布局中預設的是水平的
xml中他預設是這麼設定的 <ProgressBar style="?android:attr/progressBarStyleHorizontal"
呵呵,痛點出來了,這個如果你想用代碼設定的話,告訴你很抱歉沒有設定風格的方法。有人會說了ProgressBar 中不是有個setScrollBarStyle(int style)方法麼。
那麼我請你測試完了在說話。這個方法是無效的,請看API的描述。然後我查源碼想找出水平方向風格使用了那些設定介面,
我們可以看下progressBarStyleHorizontal樣式中給View設定了哪些屬性,我們找到framework下的res目錄下的values/Theme.xml檔案,搜尋progressBarStyleHorizontal會發現如下行:
<item name="progressBarStyleHorizontal">@android:style/Widget.ProgressBar.Horizontal</item>
該主題對應的Widget樣式是Widget.ProgressBar.Horizontal,我們在同樣的的目錄下開啟style.xml檔案,搜尋該樣式,可以找到如下代碼:
<style name="Widget.ProgressBar.Horizontal">
<item name="android:indeterminateOnly">false</item>
<item name="android:progressDrawable">@android:drawable/progress_horizontal</item>
<item name="android:indeterminateDrawable">@android:drawable/progress_indeterminate_horizontal</item>
<item name="android:minHeight">20dip</item>
<item name="android:maxHeight">20dip</item>
</style>
好了,看到這裡告訴你,你可以不使用<item name="progressBarStyleHorizontal">@android:style/Widget.ProgressBar.Horizontal</item>
而使用
android:indeterminateOnly="false"
android:progressDrawable="@android:drawable/progress_horizontal"
android:indeterminateDrawable="@android:drawable/progress_indeterminate_horizontal"
android:minHeight="20dip"
android:maxHeight="20dip" />
同樣可以實現水平進度條。我知道大家都會使用那一行而不使用這麼多行。我明白,我只是告訴你原理而已。
好的,你知道我喜歡使用代碼布局的,然後走代碼路線則是
progressBar.setIndeterminate(false);
progressBar.setProgressDrawable(getResources().getDrawable(android.R.drawable.progress_horizontal));
progressBar.setIndeterminateDrawable(getResources().getDrawable(android.R.drawable.progress_indeterminate_horizontal));
progressBar.setMinimumHeight(20);
結果是ProgressBar確實變成了橫條,但並沒有顯示成進度條的樣子,我們仔細對比一下純Java代碼和xml布局檔案之間差異,我們發現
android:indeterminateOnly="false"和 progressBar.setIndeterminate(false);
並不完全一樣布局檔案的屬性有一個Only結尾但代碼中並沒有,我們尋找Api發現並沒有setIndeterminateOnly這樣的一個方法。
我們開啟ProgressBar的原始碼,找到.setIndeterminate(false) 方法。
我們這時候可以發現Indeterminate和IndeterminateOnly並不是同一個東西,
這時我們應該想的到,只要我們把IndeterminateOnly的值變成false就可以使ProgressBar變成進度條的樣式,
我們尋找所有的代碼,發現並沒有提供相應的公開方法來修改該屬性的值。
也就是說,我們討論了那麼久發現根本就無法通過純程式碼的形式來建立一個水平進度條樣式的ProgressBar.
但是。。。某人說可以使用反射改變一個類的私人變數的值。內容比較抽象,這裡還是略過吧,因為我發現它必須知道變數名才能反射成功,
但我查詢後發現有些版本的變數名是不一樣的咧,這個版本用的mIndeterminateOnly,那個版本用的mOnlyIndeterminate(2.2版)
所以這個地方我果斷放棄了純程式碼布局,使用
ProgressBar pb = new ProgressBar(context, null,android.R.attr.progressBarStyleHorizontal); 安逸了~~~~ 這隻是第一個問題哦
2.使用toast的時候需要注意,如果你需要那個背景框就必須makeToast. 如果你喜歡乾淨的話 可以使用new Toast(context)然後再設定一些屬性之類的
如果只想要toast的短暫顯示的功能,介面完全自訂的話 推薦使用new Toast(context),最後大家要養成看源碼的習慣哦,有時候還是需要自己動手,
豐衣足食啊