『壹』 android studio中使用為什麼ctrl+shift+T 搜不到activity源碼
按兩下shift或者按ctrl+n ,恩這個是AS的快捷鍵
『貳』 求一android程序源碼 讓小球沿指定路徑運動
import android.app.Activity;
import android.os.Bundle;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnTouchListener;
import android.widget.LinearLayout;
public class MoveballActivity extends Activity {
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
LinearLayout root = (LinearLayout)findViewById(R.id.root);
final DrawView draw = new DrawView(this);
draw.setMinimumWidth(300);
draw.setMinimumHeight(500);
draw.setOnTouchListener(new OnTouchListener(){
public boolean onTouch(View arg0, MotionEvent event){
draw.currentX = event.getX();
draw.currentY = event.getY();
draw.invalidate();
return true ;
}
});
root.addView(draw);
}
}
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.view.View;
public class DrawView extends View{
public float currentX = 40 ;
public float currentY = 50 ;
public DrawView (Context context){
super(context);
}
public void onDraw(Canvas canvas){
super.onDraw(canvas);
//創建畫筆
Paint p = new Paint();
//設置畫筆的顏色
p.setColor(Color.RED);
//繪制一個小圓(作為小球)
canvas.drawCircle(currentX, currentY, 15, p);
}
}
跟隨手指移動的小球,參考一下吧。
『叄』 初學Android開發!求一個完整的詳細的Android小程序源碼參考!
媒體播放器源碼Audio.java
package org.example.audio;
import android.app.Activity;
import android.media.MediaPlayer;
import android.os.Bundle;
import android.view.KeyEvent;
public class Audio extends Activity {
private MediaPlayer up, down, left, right, enter;
private MediaPlayer a, s, d, f;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
// Native rate is 44.1kHz 16 bit stereo, but
// to save space we just use MPEG-3 22kHz mono
up = MediaPlayer.create(this, R.raw.up);
down = MediaPlayer.create(this, R.raw.down);
left = MediaPlayer.create(this, R.raw.left);
right = MediaPlayer.create(this, R.raw.right);
enter = MediaPlayer.create(this, R.raw.enter);
a = MediaPlayer.create(this, R.raw.a);
s = MediaPlayer.create(this, R.raw.s);
d = MediaPlayer.create(this, R.raw.d);
f = MediaPlayer.create(this, R.raw.f);
}
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
MediaPlayer mp;
switch (keyCode) {
case KeyEvent.KEYCODE_DPAD_UP:
mp = up;
break;
case KeyEvent.KEYCODE_DPAD_DOWN:
mp = down;
break;
case KeyEvent.KEYCODE_DPAD_LEFT:
mp = left;
break;
case KeyEvent.KEYCODE_DPAD_RIGHT:
mp = right;
break;
case KeyEvent.KEYCODE_DPAD_CENTER:
case KeyEvent.KEYCODE_ENTER:
mp = enter;
break;
case KeyEvent.KEYCODE_A:
mp = a;
break;
case KeyEvent.KEYCODE_S:
mp = s;
break;
case KeyEvent.KEYCODE_D:
mp = d;
break;
case KeyEvent.KEYCODE_F:
mp = f;
break;
default:
return super.onKeyDown(keyCode, event);
}
mp.seekTo(0);
mp.start();
return true;
}
}
『肆』 Android源碼解析Window系列第(一)篇---Window的基本認識和Activity的載入流程
您可能聽說過View ,ViewManager,Window,PhoneWindow,WindowManager,WindowManagerService,可是你知道這幾個類是什麼關系,幹嘛用的。概括的來說,View是放在Window中的,Window是一個抽象類,它的具體實現是PhoneWindow,PhoneWindow還有個內部類DecorView,WindowManager是一個interface,繼承自ViewManager,它是外界訪問Window的入口,,提供了add/remove/updata的方法操作View,WindowManager與WindowManagerSerice是個跨進程的過程,WindowManagerService的職責是對系統中的所有窗口進行管理。如果您不太清楚,建議往下看,否則就不要看了。
Android系統的Window有很多種,大體上來說,Framework定義了三種窗口類型;
這就是Framework定義了三種窗口類型,這三種類型定義在WindowManager的內部類LayoutParams中,WindowManager講這三種類型 進行了細化,把每一種類型都用一個int常量來表示,這些常量代表窗口所在的層,WindowManagerService在進行窗口疊加的時候,會按照常量的大小分配不同的層,常量值越大,代表位置越靠上面, 所以我們可以猜想一下,應用程序Window的層值常量要小於子Window的層值常量,子Window的層值常量要小於系統Window的層值常量。 Window的層級關系如下所示。
上面說了Window分為三種,用Window的type區分,在搞清楚Window的創建之前,我們需要知道怎麼去描述一個Window,我們就把Window當做一個實體類,給我的感覺,它必須要下面幾個欄位。
實際上WindowManager.LayoutParams對Window有很詳細的定義。
提取幾個重要的參數
Window是一個是一個抽象的概念,千萬不要認為我們所看到的就是Window,我們平時所看到的是視圖,每一個Window都對應著一個View,View和Window通過ViewRootImpl來建立聯系。有了View,Window的存在意義在哪裡呢,因為View不能單獨存在,它必須依附著Window,所以有視圖的地方就有Window,比如Activity,一個Dialog,一個PopWindow,一個菜單,一個Toast等等。
通過上面我們知道視圖和Window的關系,那麼有一個問題,是先有視圖,還是先有Window。這個答案只有在源碼中找了。應用程序的入口類是ActivityThread,在ActivityThread中有performLaunchActivity來啟動Activity,這個performLaunchActivity方法內部會創建一個Activity。
如果activity不為null,就會調用attach,在attach方法中通過PolicyManager創建了Window對象,並且給Window設置了回調介面。
PolicyManager的實現類是Policy
這樣Window就創建出來了, 所以先有Window,後有視圖,視圖依賴Window存在 ,再說一說視圖(Activity)為Window設置的回調介面。
Activity實現了這個回調介面,當Window的狀態發生變化的時候,就會回調Activity中實現的這些介面,有些回調介面我們還是熟悉的,dispatchTouchEvent,onAttachedToWindow,onDetachedFromWindow等。
下面分析view是如何附屬到window上的,通過上面可以看到,在attach之後就要執行callActivityOnCreate,在onCreate中我們會調用setContentView方法。
getWindow獲取了Window對象,Window的具體實現類是PhoneWindow,所以要看PhoneWindow的setContentView方法。
這里涉及到一個mContentParent變數,他是一個DecorView的一部分,DecorView是PhoneWindow的一個內部類,我先介紹一下關於DecorView的知識。
DecorView是Activity的頂級VIew,DecorView繼承自FrameLayout,在DecorView中有上下兩個部分,上面是標題欄,下面是內容欄,我們通過PhoneWindow的setContentView所設置的布局文件是加到內容欄(mContentParent)裡面的,View層的事件都是先經過DecorView在傳遞給我們的View的。
OK在回到setContentView的源碼分析,我們可以得到Activity的Window創建需要三步。
- 1、 如果沒有DecorView,在installDecor中創建DecorView。
- 2、將View添加到decorview中的mContentParent中。
- 3、回調Activity的onContentChanged介面。
先看看第一步,installDecor的源碼
installDecor中調用了generateDecor,繼續看
直接給new一個DecorView,有了DecorView之後,就可以載入具體的布局文件到DecorView中了,具體的布局文件和系統和主題有關系。
在看第二步,將View添加到decorview中的mContentParent中。
直接將Activity視圖加到DecorView的mContentParent中,最後一步,回調Activity的onContentChanged介面。在Activity中尋找onContentChanged方法,它是個空實現,我們可以在子Activity中處理。
到此DecorView被創建完畢,我們一開始從Thread中的handleLaunchActivity方法開始分析,首先載入Activity的位元組碼文件,利用反射的方式創建一個Activity對象,調用Activity對象的attach方法,在attach方法中,創建系統需要的Window並為設置回調,這個回調定義在Window之中,由Activity實現,當Window的狀態發生變化的時候,就會回調Activity實現的這些回調方法。調用attach方法之後,Window被創建完成,這時候需要關聯我們的視圖,在handleLaunchActivity中的attach執行之後就要執行handleLaunchActivity中的callActivityOnCreate,在onCreate中我們會調用setContentView方法。通過setContentView,創建了Activity的頂級View---DecorView,DecorView的內容欄(mContentParent)用來顯示我們的布局。 這個是我們上面分析得到了一個大致流程,走到這里,這只是添加的過程,還要有一個顯示的過程,顯示的過程就要調用handleLaunchActivity中的handleResumeActivity方法了。最後會調用makeVisible方法。
這裡面首先拿到WindowManager對象,用tWindowManager 的父介面ViewManager接收,ViewManager可以
最後調用 mDecor.setVisibility(View.VISIBLE)設置mDecor可見。到此,我們終於明白一個Activity是怎麼顯示在我們的面前了。
參考鏈接:
http://blog.csdn.net/feiclear_up/article/details/49201357
『伍』 如何查看Android源碼
當我們在eclipse中開發android程序的時候,往往需要看源代碼(可能是出於好奇,可能是讀源碼習慣),那麼如何查看Android源代碼呢?
比如下面這種情況
假設我們想參看Activity類的源代碼,按著Ctrl鍵,左擊它,現實的結果卻看不到代碼的,提示的信息便是「找不到Activity.class文件」。
此時點擊下面的按鈕,「Change Attached Source…」,選擇android源代碼所在位置,便彈出圖三的對話框。
第一種是選擇工作目錄,即已經存在的android應用程序源代碼。
第二種分兩種方式
(1)選擇External File…按鈕,添加Jar格式文件或者zip格式文件路徑;
(2)選擇External Floder…按鈕,添加文件夾所在路徑。
下面問題就來了,源代碼在哪裡?不能憑空產生阿。
可以通過Android SDK Manager進行源代碼下載;(推薦該種方法),如圖四
勾選Source for Android SDK,進行下載即可。
此外也可通過其他途徑下載,網上有很多共享的資源。
這里選擇第二種方式的(2)方法,選擇源碼所在目錄(即圖四下載源代碼目錄所在路徑),如圖五
點擊「OK」按鈕,此時,Activity文件便能夠查看源代碼了,如圖六。
這樣就大功告成了!!!
『陸』 Android 10.0 Activity的啟動流程
本文主要學習記錄,基於Android 10的源碼,有錯誤歡迎指正,主要目的是梳理流程圖。
以進程為單位的調用棧圖如下:
1.activity中的startActivity方法最終都會通過拿到ATSM的代理IActivityTaskManager調用的startActivity;
2.之後進入system server進程中的ATMS startActivity,ATMS 經過收集Intent信息,然後使用ActivityStackSupervisor.startSpecificActivityLocked,如果進程已經存在,則直接使用realStartActivityLocked,通過App的binder客戶端的代理ApplicationThread調用回到bindApplication,走入Activity的啟動流程;如果進程不存在則通過socket鏈接Zygote,請求fork新的進程;
3.App進程創建完成後,進程啟動會調用ActivityThread.main方法,初始化主線程Handler,接著走入attach方法,然後通過AMS的代理調用AMS的attachApplication方法,並將App進程的通信代理ApplicationThread傳入AMS;
4.AMS獲取到ATMS調用ApplicationThread的bindApplication回到App進程的ActivityThread.ApplicationThread.bindApplication方法中,然後使用Handler切換到主線程執行handleBindApplication,這里初始化了App的進程名字、時間,用戶的硬體配置,包括App的文件系統,創建了App的Context實例,Instrumentation實例,調用App的onCreate回調方法,同時告訴AMS APP初始化工作完畢;
5.AMS接著會調用ATMS的attachApplication,最後調用ClientLifecycleManager的scheleTransaction方法,通過App的Binder代理ApplicationThread回到ActivityThread;
6.進入ActivityThread.ApplicationThread.scheleTransaction方法之後就進入了Activity的onStart、onResume回調
創建進程之前的過程主要是AMS的內部信息收集的判斷的過程,下面主要看一下App進程啟動的源碼流程
從應用進程被創建開始,ActivityThread.main被執行
調用ActivityThread的attach方法,然後將activity和AMS通信的Binder代理IApplicationThread實例傳入AMS
接著進入AMS進程,ActivityManagerService.attachApplicationLocked
1.thread.bindApplication :該方法主要講App進程的配置信息通過IApplicationThread Binder通信回傳到ActivityThread中
2.mAtmInternal.attachApplication :mAtmInternal實際就是ActivityTaskManager的實例,通過LocalServices載入
那麼這里相當於走到了ActivityTaskManagerServer的attachApplication中
先看第一條:
注意:ActivityThread中存在於Binder通信的代理--》ApplicationThread extends IApplicationThread.Stub
ActivityThread--》ApplicationThread--》bindApplication
這里的bindApplication主要初始化了AppBindData,然後發送BIND_APPLICATION給APP的主線程BIND_APPLICATION,最後執行了handleBindApplication
handleBindApplication如下:
ActivityThread--》class H extends Handler
該方法主要在App進程中對App的一些硬體資源配置申請的屬性、App的文件夾等完成App基本信息的初始化
接著看第二條:mAtmInternal.attachApplication
mAtmInternal.attachApplication最終會調用mRootActivityContainer.attachApplication(wpc)
RootActivityContainer.attachApplication
接著調用ActivityStackSupervisor.realStartActivityLocked開始創建Activity
ActivityStackSupervisor.realStartActivityLocked
創建ClientLifecycleManager和ClientTransactionHandler來輔助管理Activity的生命周期
注意
clientTransaction.addCallback是LaunchActivityItem
lifecycleItem是ResumeActivityItem
ClientLifecycleManager.scheleTransaction最終會調用ClientTransaction的schele方法
那麼這個mClient是IApplicationThread的實例,那麼此時也就回到了ActivityThread的ApplicationThread中
ActivityThread的ApplicationThread中
因為ActivityThread繼承ClientTransactionHandler,所以到了ClientTransactionHandler中
通過Handler發送消息EXECUTE_TRANSACTION到H中
接著TransactionExecutor的execute方法
LaunchActivityItem.execute方法
client其實是在ActivityThread的實例,那麼就回到了ActivityThread的handleLaunchActivity
接著調用performLaunchActivity
在performLaunchActivity中,主要是載入App的資源包,然後創建了Activity的context實例,並創建了Activity的實例,接著調用activity.attach方法,attach執行完之後調用了onCreate方法。
activity.attach
activity.attach中主要
1.創建了PhoneWindow實例
2.設置了Window介面的監聽
3.初始化了成員變數,包括線程和WindowManager
到此Oncreate已經完成,那麼OnStart和OnResume去哪了?
TransactionExecutor的execute方法
之前們只分析了executeCallbacks,接著executeLifecycleState方法
TransactionExecutor的executeLifecycleState方法
cycleToPath:lifecycleItem即為ResumeActivityItem
第一點:
int finish = lifecycleItem.getTargetState()
lifecycleItem對應ResumeActivityItem,如下:
ResumeActivityItem的getTargetState方法
對應ActivityLifecycleItem中的枚舉類型:
第二點:ActivityClientRecord中的mLifecycleState,由於在前面已經執行了handleLaunchActivity所以mLifecycleState=1
對應ActivityLifecycleItem中的枚舉類型:
PRE_ON_CREATE = 0
所以final int star = 1
接著看getLifecyclePath,此時start=1,finish=3
那麼返回的IntArray就是2
接著看performLifecycleSequence
最終執行的是handleStartActivity所以最終走到了ActivityThread的handleResumeActivity
兩點:
調用activity.performStart
調用Instrumetation.callActivityOnPostCreate
performStart方法:
調用了Instrumentation.callActivityOnStart方法:
最終到了activity的onStart方法
第二點:Instrumentation.callActivityOnPostCreate
上面主要走了cycleToPath,接著ResumeActivityItem.execute
調用了handleResumeActivity方法
handleResumeActivity最終調用performResumeActivity
調用了Instrumentation.callActivityOnResume,
到了activity.onResume()方法
參考文章: https://blog.csdn.net/u011386173/article/details/87802765
『柒』 android activitymanager 在源碼哪個目錄
android的源碼首先需要你從Android SDK Manager裡面下載,然後在你的sdk中才看得到
『捌』 怎樣在eclipse中看android源碼
當我們在eclipse中開發android程序的時候,往往需要看源代碼(可能是出於好奇,可能是讀源碼習慣),那麼如何查看Android源代碼呢?
比如下面這種情況
圖六
這樣就大功告成了!!!
『玖』 sublime text3 查看android的ActivityManagerService.java源碼時,Ctrl+R列不出所函數
最近在用Sublime Text 3,很多人用它寫前端,對Java研究較少。按網上的教程進行設置之後,對中文的支持仍然不盡人意,在編譯窗口往往將中文顯示為空白甚至報錯。 一直在用cmd命令行手動編譯運行,不勝其煩。今天調試了各步聚的參數,終於完美解決此問題。 以下步驟依據網友的心得修改而成: 方法一: 打開Sublime Text 3,依次點擊Preference, Browse Packages,在打開的窗口中雙擊User文件夾,新建文件JavaC.sublime-build,用記事本打開,粘貼下面的代碼並保存關閉: { "cmd": ["javac","-encoding","UTF-8","-d",".","$file"], "file_regex": "^(...*?):([0-9]*):?([0-9]*)", "selector": "source.java", "encoding":"GBK", //執行完上面的命令就結束 // 下面的命令需要按Ctrl+Shift+b來運行 "variants": [ { "name": "Run", "shell": true, "cmd" : ["start","cmd","/c", "java ${file_base_name} &echo. & pause"], // /c是執行完命令後關閉cmd窗口, // /k是執行完命令後不關閉cmd窗口。 // echo. 相當於輸入一個回車
『拾』 求一個android開發中從一個activity中通過httpurlconnection發送圖片到servlet,並且servlet接收到的源碼
//伺服器servlet代碼
publicvoid doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
String temp=request.getSession().getServletContext().getRealPath("/")+"temp"; //臨時目錄
System.out.println("temp="+temp);
String loadpath=request.getSession().getServletContext().getRealPath("/")+"Image"; //上傳文件存放目錄
System.out.println("loadpath="+loadpath);
DiskFileUpload fu =new DiskFileUpload();
fu.setSizeMax(1*1024*1024); // 設置允許用戶上傳文件大小,單位:位元組
fu.setSizeThreshold(4096); // 設置最多隻允許在內存中存儲的數據,單位:位元組
fu.setRepositoryPath(temp); // 設置一旦文件大小超過getSizeThreshold()的值時數據存放在硬碟的目錄
//開始讀取上傳信息
int index=0;
List fileItems =null;
try {
fileItems = fu.parseRequest(request);
System.out.println("fileItems="+fileItems);
} catch (Exception e) {
e.printStackTrace();
}
Iterator iter = fileItems.iterator(); // 依次處理每個上傳的文件
while (iter.hasNext())
{
FileItem item = (FileItem)iter.next();// 忽略其他不是文件域的所有表單信息
if (!item.isFormField())
{
String name = item.getName();//獲取上傳文件名,包括路徑
name=name.substring(name.lastIndexOf("\\")+1);//從全路徑中提取文件名
long size = item.getSize();
if((name==null||name.equals("")) && size==0)
continue;
int point = name.indexOf(".");
name=(new Date()).getTime()+name.substring(point,name.length())+index;
index++;
File fNew=new File(loadpath, name);
try {
item.write(fNew);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
else//取出不是文件域的所有表單信息
{
String fieldvalue = item.getString();
//如果包含中文應寫為:(轉為UTF-8編碼)
//String fieldvalue = new String(item.getString().getBytes(),"UTF-8");
}
}
String text1="11";
response.sendRedirect("result.jsp?text1="+ text1);
}
//android 代碼
publicclass PhotoUpload extends Activity {
private String newName ="image.jpg";
private String uploadFile ="/sdcard/image.JPG";
private String actionUrl ="http://192.168.0.71:8086/HelloWord/myForm";
private TextView mText1;
private TextView mText2;
private Button mButton;
@Override
publicvoid onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.photo_upload);
mText1 = (TextView) findViewById(R.id.myText2);
//"文件路徑:\n"+
mText1.setText(uploadFile);
mText2 = (TextView) findViewById(R.id.myText3);
//"上傳網址:\n"+
mText2.setText(actionUrl);
/* 設置mButton的onClick事件處理 */
mButton = (Button) findViewById(R.id.myButton);
mButton.setOnClickListener(new View.OnClickListener()
{
publicvoid onClick(View v)
{
uploadFile();
}
});
}
/* 上傳文件至Server的方法 */
privatevoid uploadFile()
{
String end ="\r\n";
String twoHyphens ="--";
String boundary ="*****";
try
{
URL url =new URL(actionUrl);
HttpURLConnection con=(HttpURLConnection)url.openConnection();
/* 允許Input、Output,不使用Cache */
con.setDoInput(true);
con.setDoOutput(true);
con.setUseCaches(false);
/* 設置傳送的method=POST */
con.setRequestMethod("POST");
/* setRequestProperty */
con.setRequestProperty("Connection", "Keep-Alive");
con.setRequestProperty("Charset", "UTF-8");
con.setRequestProperty("Content-Type",
"multipart/form-data;boundary="+boundary);
/* 設置DataOutputStream */
DataOutputStream ds =
new DataOutputStream(con.getOutputStream());
ds.writeBytes(twoHyphens + boundary + end);
ds.writeBytes("Content-Disposition: form-data; "+
"name=\"file1\";filename=\""+
newName +"\""+ end);
ds.writeBytes(end);
/* 取得文件的FileInputStream */
FileInputStream fStream =new FileInputStream(uploadFile);
/* 設置每次寫入1024bytes */
int bufferSize =1024;
byte[] buffer =newbyte[bufferSize];
int length =-1;
/* 從文件讀取數據至緩沖區 */
while((length = fStream.read(buffer)) !=-1)
{
/* 將資料寫入DataOutputStream中 */
ds.write(buffer, 0, length);
}
ds.writeBytes(end);
ds.writeBytes(twoHyphens + boundary + twoHyphens + end);
/* close streams */
fStream.close();
ds.flush();
/* 取得Response內容 */
InputStream is = con.getInputStream();
int ch;
StringBuffer b =new StringBuffer();
while( ( ch = is.read() ) !=-1 )
{
b.append( (char)ch );
}
/* 將Response顯示於Dialog */
showDialog("上傳成功"+b.toString().trim());
/* 關閉DataOutputStream */
ds.close();
}
catch(Exception e)
{
showDialog("上傳失敗"+e);
}
}
/* 顯示Dialog的method */
privatevoid showDialog(String mess)
{
new AlertDialog.Builder(PhotoUpload.this).setTitle("Message")
.setMessage(mess)
.setNegativeButton("確定",new DialogInterface.OnClickListener()
{
publicvoid onClick(DialogInterface dialog, int which)
{
}
})
.show();
}
}
扣扣 2605 14095 可以提供開發幫助