过去我一直在为这个解决方案做好48小时(我有一些额外的时间不要怪我),我可以肯定地告诉你们:
>使用AppCompat主题和正常的微调给你免费的涟漪(yay!)。如果您有一个自定义Spinner,请确保扩展AppCompatSpinner,并获得一些很好的主题。引用AppCompatSpinner javadoc:
A Spinner which supports compatible features on older version of the platform, including:
Allows dynamic tint of it background via the background tint methods in ViewCompat.
Allows setting of the background tint using backgroundTint and backgroundTintMode.
Allows setting of the popups theme using popupTheme.
This will automatically be used when you use Spinner in your layouts. You should only need to manually use this class when writing custom views.
>没有办法通过扩展ANY类来检索显示的PopupWindow。有很多嵌套类有助于功能(扰流器:它们大都是私有的)。
>您可以在您的主题(woohoo!)中静态地自定义弹出窗口的输入和退出转换。我目前正在使用AppCompat v23进行一些调查,我发现:
>定制ListPopupWindow LOLLIPOP及以上的样式
?attr/listChoiceBackgroundIndicator
@drawable/popup_background_material
@dimen/floating_window_z
@empty
@transition/popup_window_enter
@transition/popup_window_exit
0dip
0dip
wrap_content
>自定义它的样式前LOLLIPOP:
?attr/listChoiceBackgroundIndicator
@drawable/abc_popup_background_mtrl_mult
0dip
0dip
wrap_content
>这是你在主题中设置的:
// From the constructor listPopupWindowStyle is the
// theme attribute you're looking for.
public ListPopupWindow(Context context, AttributeSet attrs) {
this(context, attrs, R.attr.listPopupWindowStyle);
}
也就是说,我仍然在获得您的具体细节,但我通过克隆2个类:AppCompatSpinner和ListPopupWindow并将公共getPopup()getter添加到克隆的ListPopupWindow代码中,因此可以在我的克隆的AppCompatSpinner中访问。这打开了几个机会。一个例子是我的centerPopup()方法,它应该根据spinnerItem的中心(在微调框视图本身显示的所选项目)和spinnerDropdownItem(显示为列表项的单个视图)中移动布局的弹出窗口的位置落下)。然后在调用super.show()之后,在DropdownPopup.show()中调用centerPopup()方法,
private void centerPopup(boolean updateListSelection) {
boolean aboveAnchor = getPopup().isAboveAnchor();
int[] spinnerLocation = new int[2];
int[] popupLocation = new int[2];
ListView listView = getListView();
/*
Popup is anchored at spinner TOP LEFT when it is set to overlap else at BOTTOM LEFT
Also seems the windowlayoutparams generated for popup is wrapcontent for width and height
As a result popup locationOnScreen returns [0, 0] which is relative to the window.
We can take it as relative to spinner location and add spinnerLocation X value to give
left edge of popup
*/
MaterialSpinner.this.getLocationInWindow(spinnerLocation);
int spMidX = spinnerLocation[0] + (MaterialSpinner.this.getWidth() / 2);
int spMidY = spinnerLocation[1] + (MaterialSpinner.this.getHeight() / 2);
Rect spinnerBgdPadding = new Rect();
MaterialSpinner.this.getBackground().getPadding(spinnerBgdPadding);
// ----- BUG - returns erroneous height
// Ideally should measure one of the drop down list children and give a height
// exactly as it wouldwhen laid out eventually.
// Works only for lists with homogenously tall content
View child = listView.getAdapter().getView(0, null, listView);
child.setLayoutParams(new LayoutParams(WRAP_CONTENT, WRAP_CONTENT));
child.measure(
MeasureSpec.makeMeasureSpec(listView.getWidth() - listView.getPaddingLeft() - listView.getPaddingRight(), MeasureSpec.AT_MOST),
MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED)
);
int listItemHeight = child.getMeasuredHeight();
// ----- /BUG
getPopup().getContentView().getLocationInWindow(popupLocation);
int popMidX = spinnerLocation[0] + (getPopup().getWidth()) / 2;
int popMidY = spinnerLocation[1] + (listItemHeight / 2);
int hoff = getHorizontalOffset();
int voff = getVerticalOffset();
int xoff = spMidX - popMidX - hoff - spinnerBgdPadding.left;
int yoff = spMidY - popMidY - voff;
getPopup().update(spinnerLocation[0] + xoff, spinnerLocation[1] + yoff, -1, -1, true);
if (updateListSelection)
listView.setSelectionFromTop(MaterialSpinner.this.getSelectedItemPosition(), 0)
;
// getPopup().update(MaterialSpinner.this, xoff, yoff, -1, -1);
// int numVisItems = listView.getLastVisiblePosition() - getFirstVisiblePosition();
}
如果返回正确的listItemHeight,弹出窗口不仅应该出现在微调框上,而且文本中心也应该对齐。 (由于背景和填充相关问题,可能会被某些像素关闭,但可以解决)。
一旦居中,下一步是将dropDownList selectedPosition View滚动到popupWindow的中心,并相应地更新yoff Y-offset。
popupEnterTransition属性仅限于LOLLIPOP,但如果这不是一个问题,您可以在其中插入扩展向上的转换,这将使您获得所需的效果。我还没有尝试过,但我也认为一个更好的动画将是一个透明的影响从旋转中心(它看起来像您的规格视频)。
但是所有这些都是好的…在理论上x_x哈哈