我有一个Activity
,其中包含3 EditText
个自定义视图,该视图用作专用键盘,可将信息添加到EditText
中。
目前我正在将Activity
传递到视图中,以便我可以获取当前关注的编辑文本并更新自定义键盘中的内容。
有没有办法引用父活动并获取当前关注的EditText
而不将活动传递到视图中?
答案 0 :(得分:256)
我刚刚从official support library的MediaRouter中提取了该源代码,到目前为止它工作正常:
private Activity getActivity() {
Context context = getContext();
while (context instanceof ContextWrapper) {
if (context instanceof Activity) {
return (Activity)context;
}
context = ((ContextWrapper)context).getBaseContext();
}
return null;
}
答案 1 :(得分:167)
以下方法可以帮助您
Activity host = (Activity) view.getContext()
;和view.isFocused()
答案 2 :(得分:4)
我带了Gomino' answer并对其进行了修改以完全适合myUtils.java,因此我可以随时随地使用它。希望有人觉得它有用:)
abstract class myUtils {
public static Activity getActivity(View view) {
Context context = view.getContext();
while (context instanceof ContextWrapper) {
if (context instanceof Activity) {
return (Activity)context;
}
context = ((ContextWrapper)context).getBaseContext();
}
return null;
}
}
答案 3 :(得分:2)
我喜欢用Kotlin编写的解决方案
tailrec fun Context?.activity(): Activity? = when (this) {
is Activity -> this
else -> (this as? ContextWrapper)?.baseContext?.activity()
}
在View
类中的用法
context.activity()
已编译的代码:
public static final Activity activity(Context context) {
while (!(context instanceof Activity)) {
if (!(context instanceof ContextWrapper)) {
context = null;
}
ContextWrapper contextWrapper = (ContextWrapper) context;
if (contextWrapper == null) {
return null;
}
context = contextWrapper.getBaseContext();
if (context == null) {
return null;
}
}
return (Activity) context;
}
答案 4 :(得分:0)
在Android 7+中,视图无法再访问封闭活动,因此view.getContext()
无法再投射到活动中。
相反,下面的代码适用于Android 7+和6:
private static Activity getActivity(final View view) {
return (Activity) view.findViewById(android.R.id.content).getContext();
}
答案 5 :(得分:0)
[注意:看到此答案后,请参阅我的其他文章: https://stackoverflow.com/a/51100507/787399 ]
我对此有不同的处理方法,并且可行。
我要做的是创建一个自定义应用程序扩展类,并将其标记在清单中:-
public class MyApplication extends Application {
private AppCompatActivity currentActivity;
@Override
public void onCreate() {
super.onCreate();
}
public void setCurrentActivity(AppCompatActivity _activity){
this.currentActivity = _activity;
}
public AppCompatActivity getCurrentActivity() {
return currentActivity;
}
}
和
清单中的MyApplication:-
...
<application
android:name=".core.MyApplication"
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/AppTheme">
...
然后在我的BaseActivity(扩展AppCompatActivity的抽象类,意味着所有活动都将其扩展, 具有共同的功能,可以委托要在所有组件,片段,适配器等中访问的类。):-
...
@Override
protected void onResume() {
super.onResume();
((MyApplication) getApplicationContext()).setCurrentActivity(this);
}
...
然后在我的customViews中(扩展视图,TextViews以应用语言环境设置和字体):-
...
private void setFontFromAsset(Context context, AttributeSet attrs, int defStyle) {
BaseActivity activity = (BaseActivity)((MyApplication) context.getApplicationContext()).getCurrentActivity();
FontAndLocaleManager fontAndLocaleManager = activity.getFontAndLocaleManager();
fontAndLocaleManager.setFontFromAsset(this, R.styleable.FontButton, R.styleable.FontButton_btFontFace, attrs, defStyle);
}
...
此解决方案使用继承,委托类的概念以及可以在任何地方访问应用程序上下文的知识(可在清单中用您自己的应用程序扩展类替换,以及活动的生命周期,在恢复时您可以告诉应用程序(MyApplication)这是您当前的活动。
现在,就像您要更改应用程序的语言环境一样,更改它的最佳位置就是在setContentView(layout_id)
方法中调用activity
的{{1}}之前。因此,一旦更改onCreate(Bundle restoreState)
,就必须将控件发送回locale
屏幕,以便立即看到效果。
您还可以刷新dashboard/home
,因为您知道activity
中getCurrentActivity()
中的哪个是最新的。
要设置应用程序的语言环境,请参阅Set Locale programmatically
快乐编码...:-)
答案 6 :(得分:0)
用于查看父活动的View的Kotlin扩展属性:
val View.activity: Activity?
get() {
var ctx = context
while (true) {
if (!ContextWrapper::class.java.isInstance(ctx)) {
return null
}
if (Activity::class.java.isInstance(ctx)) {
return ctx as Activity
}
ctx = (ctx as ContextWrapper).baseContext
}
}
答案 7 :(得分:0)
只是想注意,如果您知道您的视图在 Fragment
内,您可以这样做:
FragmentManager.findFragment(this).getActivity();
从您的 onAttachedToWindow
或 onDraw
调用它,您不能提前调用它(例如 onFinishInflate
),否则您会收到异常。
如果您不确定您的视图是否在 Fragment
内,请参考其他答案,例如Gomino,只是想把它扔在那里。
答案 8 :(得分:-1)
对我来说这很有效:
Context context = SdkUtils.getRootViewContext(getRootView());
然后按照(Activity) context
答案 9 :(得分:-1)
@Override public boolean shouldOverrideUrlLoading(WebView视图,WebResourceRequest请求){ if(request.getUrl()。getHost()。startsWith(“ pay.google.com”)){ 意图意图=新意图(Intent.ACTION_VIEW,request.getUrl()); view.getContext()。startActivity(intent); 返回true; } ... ... }