我想在单击时显示更多按钮,默认情况下应打开带有3个选项的弹出窗口,但是根据某些逻辑,选项将更改,即。根据某些条件隐藏其中一个选项。
我试图添加一个弹出菜单:
popup = new PopupMenu(this, _showMore, GravityFlags.Top);
popup.MenuInflater.Inflate(Resource.Menu.showMoreMenu, popup.Menu);
if (!string.IsNullOrEmpty(someValue))
{
popup.Menu.FindItem(Resource.Id.ABC1).SetVisible(false);
}
popup.MenuItemClick += Popup_MenuItemClick;
popup.Show();
但是在这种情况下,最初,当我拥有所有3个选项时,弹出窗口显示在按钮上方,因为显示更多按钮下方的空间较小。但是,如果我隐藏其中一个选项,则我的弹出菜单将在按钮底部打开。我希望我的弹出菜单始终在定位按钮上方打开。
然后我也尝试了
PopupWindow popupWindow = new PopupWindow(this); // inflet your layout or diynamic add view
LayoutInflater inflater = (LayoutInflater)GetSystemService(Context.LayoutInflaterService);
View view = inflater.Inflate(Resource.Layout.TestLayout, null, false);
TextView abc1 = (TextView)view.FindViewById(Resource.Id.abc1);
TextView abc2 = (TextView)view.FindViewById(Resource.Id.abc2);
TextView abc3 = (TextView)view.FindViewById(Resource.Id.abc3);
abc1.Click += abc1_Click;
abc2.Click += abc2_Click;
if (!string.IsNullOrEmpty(somecondition))
{
abc1.Visibility = ViewStates.Gone;
}
else
{
abc2.Visibility = ViewStates.Gone;
}
popupWindow.Focusable = (true);
popupWindow.Width = (WindowManagerLayoutParams.WrapContent);
popupWindow.Height = (WindowManagerLayoutParams.WrapContent);
popupWindow.ContentView = (view);
popupWindow.SetBackgroundDrawable(new ColorDrawable(Color.Transparent));
/*
//tried
var tttt= (int)TypedValue.ApplyDimension(ComplexUnitType.Dip, Resource.Dimension._15sdp, Resources.DisplayMetrics);
//tried
int test=(int)(Resource.Dimension._15sdp * Resources.DisplayMetrics.Density);
//tried
float scale = Resources.DisplayMetrics.Density;
test= (int)(Resource.Dimension._15sdp * scale + 0.5f);
//tried
var dp = Resource.Dimension._15sdp;
int pixel = (int)TypedValue.ApplyDimension(ComplexUnitType.Dip, dp, Resources.DisplayMetrics);
*/
popupWindow.ShowAsDropDown(_showMore, -220, -570); <-- fixed offset which works for 3 options
上面的代码有效,但是我设置了固定的偏移值,我认为这将无法在不同分辨率的手机上以及在隐藏菜单中的选项之一时正确呈现偏移值。
我也尝试使用ListPopupWindow,但是设置位置存在相同问题。有人可以帮我动态设置偏移量吗?
答案 0 :(得分:0)
可以这样工作吗:
int[] location = new int[2];
_showMore.getLocationOnScreen(location);
popupWindow.showAtLocation(_showMore,Gravity.NO_GRAVITY,location[0], location[1] - popupWindow.getHeight());
答案 1 :(得分:0)
您可以尝试以下代码:
fun showPopupAbove(anchor: View) {
viewAnchor = anchor
if (Build.VERSION.SDK_INT == Build.VERSION_CODES.N) {
popupWindow.showAsDropDown(anchor)
} else {
popupWindow.showAtLocation(anchor, Gravity.NO_GRAVITY, 0, 0)
}
measureSizeThenUpdatePopupWindowPosition()
}
private fun measureSizeThenUpdatePopupWindowPosition() {
val viewTreeObserver = rootView.viewTreeObserver
if (!viewTreeObserver.isAlive) {
return
}
viewTreeObserver.addOnGlobalLayoutListener(object : ViewTreeObserver.OnGlobalLayoutListener {
override fun onGlobalLayout() {
rootView.viewTreeObserver.removeOnGlobalLayoutListener(this)
val anchorRect = getRectFromView(viewAnchor)
// calculate x,y position for display popup window above/below..ect anchor view
var popupWinDownPositionX = (anchorRect.centerX() - rootView.width.toFloat() / 6).toInt()
var popupWinDownPositionY = anchorRect.top
// anchor view close to left
if (popupWinDownPositionX < 0) {
popupWinDownPositionX = 0
}
// anchor view close to top
if (popupWinDownPositionY < 0) {
popupWinDownPositionY = 0
}
// anchor view close to right
if (popupMayExceedsTheScreen(popupWinDownPositionX,
rootView.width)) {
popupWinDownPositionX = (Resources.getSystem().displayMetrics.widthPixels - rootView.width.toFloat()).toInt()
}
popupWindow.update(popupWinDownPositionX, popupWinDownPositionY,
rootView.width, rootView.height)
updateImageArrowMargin(popupWinDownPositionX)
}
})
}
您可以根据自己的目的修改popupWinDownPositionX
和popupWinDownPositionY
的值
答案 2 :(得分:0)
谢谢@LeoZhu @LeoZhu's reply。我设法使用以下代码使其工作
PopupWindow popupWindow = new PopupWindow(this); // inflet your layout or diynamic add view
LayoutInflater inflater = (LayoutInflater)GetSystemService(Context.LayoutInflaterService);
View view = inflater.Inflate(Resource.Layout.TestLayout, null, false);
TextView abc1 = (TextView)view.FindViewById(Resource.Id.abc1);
TextView abc2 = (TextView)view.FindViewById(Resource.Id.abc2);
TextView abc3 = (TextView)view.FindViewById(Resource.Id.abc3);
abc1.Click += GenerateQR_Click;
abc2.Click += PrintQR_Click;
if (!string.IsNullOrEmpty(somecode))
{
abc1.Visibility = ViewStates.Gone;
}
else
{
abc2.Visibility = ViewStates.Gone;
}
int[] location = new int[2];
_showMore.GetLocationOnScreen(location);
popupWindow.Focusable = (true);
popupWindow.Width = (WindowManagerLayoutParams.WrapContent);
popupWindow.Height = (WindowManagerLayoutParams.WrapContent);
popupWindow.ContentView = (view);
popupWindow.SetBackgroundDrawable(new ColorDrawable(Color.Transparent));
view.Measure(View.MeasureSpec.MakeMeasureSpec(0, MeasureSpecMode.Unspecified),
View.MeasureSpec.MakeMeasureSpec(0, MeasureSpecMode.Unspecified));
int yOffset = location[1] - (int)(view.MeasuredHeight );
popupWindow.ShowAtLocation(_showMore, GravityFlags.NoGravity, location[0], yOffset);