我正在动作栏上实现" KenBurns效果 "(演示在这里),如图书馆的样本所示(移动的图标除外,我自己就是这样做的).
事实上,我甚至在很久以前(这里)问过这个问题,在这一点上我甚至都不知道它的名字.我确信我找到了解决方案,但它有一些问题.
此外,因为我有时从设备显示图像,有的甚至需要旋转,所以我用一个rotatableDrawable(如图所示这里).
当前实现无法处理动态给出的多个位图(例如,来自Internet),甚至不能查看输入图像的大小.
相反,它只是以随机方式进行缩放和平移,因此很多时候它可以缩放太多/很少,并且可以显示空白空间.
这是与问题相关的代码:
private float pickScale() {
return MIN_SCALE_FACTOR + this.random.nextFloat() * (MAX_SCALE_FACTOR - MIN_SCALE_FACTOR);
}
private float pickTranslation(final int value, final float ratio) {
return value * (ratio - 1.0f) * (this.random.nextFloat() - 0.5f);
}
public void animate(final ImageView view) {
final float fromScale = pickScale();
final float toScale = pickScale();
final float fromTranslationX = pickTranslation(view.getWidth(), fromScale);
final float fromTranslationY = pickTranslation(view.getHeight(), fromScale); …Run Code Online (Sandbox Code Playgroud) animation android image-manipulation android-animation android-kenburnsview
正如标题所说.我想知道特定应用在特定时间每秒使用的字节数.
也许我可以使用" netstat "命令?但如果是这样,我如何将其过滤到特定的应用/流程?
我还需要获得一些许可吗?
目前人们说使用TrafficStats.getUidRxBytes(packageInfo.uid),但是,从这里:https://developer.android.com/reference/android/net/TrafficStats.html#getUidRxBytes (int ),它表示不支持N,我应该使用NetworkStatsManager.有没有任何使用它的例子?
也许合并的解决方案?
编辑:我试图在Android N上使用NetworkStatsManager,但我失败了.我找不到任何关于如何使用它的示例,并且关于它的所有stackOverflow问题都是类似的,因为它无法很好地使用它.如果有人知道如何使用它,请写下来.
不知何故,应用程序" Navbar Apps "允许自定义导航栏的背景,即使它不在前景中,甚至不仅仅是简单的颜色.
我认为只有当应用程序位于前台时才能改变它的颜色......
我在一些自定义的roms上看到它,甚至在播放音乐时都有特效,但我不知道即使没有自定义ROM(或root)也可以自定义它.
这是一个黑客?它们如何改变,而不仅仅是导航栏的颜色,甚至为它设置背景图像(包括动态的电池状态)?
是否也可以更改其他系统栏,例如通知栏?
它如何检查哪个应用程序位于前台(可能需要根据当前应用程序决定何时更改颜色)?它是一个新的API吗?我认为用于获取前台活动的API已被弃用,现在无论如何都没有帮助......
有时,recyclelerView的所有项目都已对用户可见.
在这种情况下,用户看到过度滚动效果并不重要,因为实际滚动和查看更多项目是不可能的.
我知道为了在RecyclerView上禁用过度滚动效果,我可以使用:
recyclerView.setOverScrollMode(View.OVER_SCROLL_NEVER);
Run Code Online (Sandbox Code Playgroud)
但无论如何都无法滚动,我无法找到何时触发此功能.
如何确定所有项目完全可见并且用户无法真正滚动?
如果它有助于假设任何东西,我总是使用LinearLayoutManager(垂直和水平)为RecyclerView.
我不得不创建一个类似微调器的视图,它具有以下行为:
我已经成功制作了这个视图(下面的代码),但出于某种原因,在Android 7.1上,我让弹出菜单出现在视图的顶部(甚至重叠它和它上面的视图),而不是它下面,因为它应该.这是它的样子,它应该是什么样子:
由于它是相当多的代码和资源,我把它全部放在一个Github存储库(这里),但这里是代码的主要部分(我在修复它的尝试是在注释中):
FullSizePopupSpinner.java
public class FullSizePopupSpinner extends android.support.v7.widget.AppCompatTextView {
private static final long ANIMATION_DURATION = 150;
private int[] mItemsTextsResIds, mItemsIconsResIds;
private int mSelectedItemPosition = -1;
private SpinnerPopupWindow mPopupWindow;
private boolean mInitialized = false;
private OnItemSelectedListener mOnItemSelectedListener;
private Drawable mClosedDrawable;
private Drawable mOpenedDrawable;
public interface OnItemSelectedListener {
void onItemSelected(FullSizePopupSpinner parent, int position, String item, int previousSelectedPosition);
void onNothingSelected(FullSizePopupSpinner parent);
}
public FullSizePopupSpinner(final Context context) {
super(context);
init(context);
}
public FullSizePopupSpinner(final Context …Run Code Online (Sandbox Code Playgroud) 可以使用以下方法将RecyclerView捕捉到其中心:
LinearSnapHelper().attachToRecyclerView(recyclerView)
Run Code Online (Sandbox Code Playgroud)
例:
MainActivity.kt
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val inflater = LayoutInflater.from(this)
recyclerView.adapter = object : RecyclerView.Adapter<RecyclerView.ViewHolder>() {
override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int) {
val textView = holder.itemView as TextView
textView.setBackgroundColor(if (position % 2 == 0) 0xffff0000.toInt() else 0xff00ff00.toInt())
textView.text = position.toString()
}
override fun getItemCount(): Int {
return 100
}
override fun onCreateViewHolder(parent: ViewGroup?, viewType: Int): RecyclerView.ViewHolder {
val view = inflater.inflate(android.R.layout.simple_list_item_1, parent, false) as TextView
val cellSize = …Run Code Online (Sandbox Code Playgroud) 应用程序使用Intent打开其他应用程序,有时使用专门的Intent.
一个例子就是Intent,从WhatsApp中选择一个联系人:
val WHATSAPP_PACKAGE_NAME = "com.whatsapp"
val whatsAppPickIntent = Intent(Intent.ACTION_PICK).setPackage(WHATSAPP_PACKAGE_NAME)
Run Code Online (Sandbox Code Playgroud)
这一般工作正常.当您希望启动应用程序时也是如此:
val launchIntent=packageManager.getLaunchIntentForPackage(WHATSAPP_PACKAGE_NAME)
Run Code Online (Sandbox Code Playgroud)
最近我被告知一个相对较新的功能,允许用户拥有同一个应用程序的多个实例.它可能在其他设备上可用,但在OnePlus设备上,它被称为"并行应用程序".以下是WhatsApp的2个实例的示例,每个实例都分配给不同的电话号码:
事实上,这可以打破Intents如何使用应用程序的单个实例.现在,Intent不知道要去哪个应用程序.发射器现在为WhatsApp显示2个图标:
如果您选择通过普通启动器图标(左侧)启动WhatsApp,则会显示以下对话框:
工作正常,但是如果你选择使用选择器意图,你仍然会得到这个对话框,但是当你从对话框中选择一个项目时,它不会让你真正对它做任何事情(打开和关闭应用程序),而显示祝酒词"不支持文件格式".
由于我没有设备,我试图通过互联网阅读它,但我只找到了与用户相关的信息,例如:
我决定尝试进一步调查,通过向告诉我的人发送APK,试图查看下一个代码是否会有所不同:
val whatsAppPickIntent = Intent(Intent.ACTION_PICK).setPackage(WHATSAPP_PACKAGE_NAME)
val queryIntentActivities: List<ResolveInfo> = packageManager.queryIntentActivities(whatsAppPickIntent, 0)
button2.setOnClickListener {
intent = Intent(Intent.ACTION_PICK)
val resolveInfo = queryIntentActivities[0]
toast("number of possible choices:" + queryIntentActivities.size)
intent.component = ComponentName(resolveInfo.activityInfo.packageName, resolveInfo.activityInfo.name)
startActivity(intent)
}
Run Code Online (Sandbox Code Playgroud)
将要显示的toast告诉我只有一件事可以处理意图,实际上当我使用它时,我会得到相同的对话框来选择使用它的实例.就像在原始的Intent中一样,它失败了同样的吐司.
编辑:后来我尝试了下一件事:我要求在启用该功能之前和之后通过使用以下代码显示ResolveInfo属性:
val launchIntent = packageManager.getLaunchIntentForPackage(WHATSAPP_PACKAGE_NAME)
val whatsAppPickIntent = Intent(Intent.ACTION_PICK).setPackage(WHATSAPP_PACKAGE_NAME)
var queryIntentActivities: List<ResolveInfo> = packageManager.queryIntentActivities(whatsAppPickIntent, 0)
var sb = StringBuilder()
queryIntentActivities[0].dump(object : Printer {
override …Run Code Online (Sandbox Code Playgroud) 为了对水平RecyclerView上的项目进行简洁概述,我们希望有一个类似于弹跳的动画,从某个位置开始,然后转到RecyclerView的开头(例如,从第3项到第0项) .
出于某种原因,我尝试的所有Interpolator类(此处提供的插图)似乎都不允许项目超出RecyclerView或反弹.
更具体地说,我尝试过OvershootInterpolator,BounceInterpolator和其他一些类似的东西.我甚至尝试过AnticipateOvershootInterpolator.在大多数情况下,它只进行简单的滚动,没有特殊效果.在AnticipateOvershootInterpolator上,它甚至不滚动...
以下是我所制作的POC的代码,以显示问题:
MainActivity.kt
class MainActivity : AppCompatActivity() {
val handler = Handler()
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val itemSize = resources.getDimensionPixelSize(R.dimen.list_item_size)
val itemsCount = 6
recyclerView.adapter = object : RecyclerView.Adapter<RecyclerView.ViewHolder>() {
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RecyclerView.ViewHolder {
val imageView = ImageView(this@MainActivity)
imageView.setImageResource(android.R.drawable.sym_def_app_icon)
imageView.layoutParams = RecyclerView.LayoutParams(itemSize, itemSize)
return object : RecyclerView.ViewHolder(imageView) {}
}
override fun getItemCount(): Int = itemsCount
override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int) {
} …Run Code Online (Sandbox Code Playgroud) 我们希望让用户从任何应用中选择视频,然后将视频剪裁为最多5秒.
为了让Uri被选中,我们让它工作正常(这里有解决方案).
至于修剪本身,我们找不到任何具有许可许可的好图书馆,除了一个名为"k4l-video-trimmer"的图书馆.例如,库"FFmpeg"被认为是非许可,因为它使用GPLv3,这要求使用它的应用程序也是开源的.此外,正如我所读,它需要相当多(约9MB).
可悲的是,这个库(k4l-video-trimmer)很老了,多年没有更新了,所以我不得不把它(这里)分叉,以便很好地处理它.它使用一个名为"mp4parser"的开源库来进行修剪.
问题是,这个库似乎只能处理文件,而不是一个Uri或者InputStream,所以即使样本在选择像普通文件一样无法访问的项目时也会崩溃,甚至还有无法处理的路径.我知道在很多情况下可以获得文件的路径,但在许多其他情况下,它不是,我也知道可以只复制文件(这里),但这不是一个好的解决方案,因为文件可能很大并占用大量空间,即使它已经可以访问.
库有两个地方使用文件:
在"K4LVideoTrimmer"文件中,在"setVideoURI"函数中,它只是获取要显示的文件大小.根据Google的文档,这里的解决方案非常简单:
public void setVideoURI(final Uri videoURI) {
mSrc = videoURI;
if (mOriginSizeFile == 0) {
final Cursor cursor = getContext().getContentResolver().query(videoURI, null, null, null, null);
if (cursor != null) {
int sizeIndex = cursor.getColumnIndex(OpenableColumns.SIZE);
cursor.moveToFirst();
mOriginSizeFile = cursor.getLong(sizeIndex);
cursor.close();
mTextSize.setText(Formatter.formatShortFileSize(getContext(), mOriginSizeFile));
}
}
...
Run Code Online (Sandbox Code Playgroud)在"TrimVideoUtils"文件中,在"startTrim"中调用"genVideoUsingMp4Parser"函数.在那里,它使用以下方法调用"mp4parser"库:
Movie movie = MovieCreator.build(new FileDataSourceViaHeapImpl(src.getAbsolutePath()));
Run Code Online (Sandbox Code Playgroud)
它说他们使用FileDataSourceViaHeapImpl(来自"mp4parser"库)来避免Android上的OOM,所以我决定继续使用它.
事实是,它有4个CTORS,都期望文件有一些变化:File,filePath,FileChannel,FileChannel + fileName. …
android filechannel inputstream android-contentresolver mp4parser
请考虑以下情形:
我认为我有一些功能,但它有一些问题:
当我成功解决#2(或#3)时,这可能是一个问题.现在,我正在使用一个使用runnable的处理程序并在其中调用此命令:
mViewPager.setCurrentItem((mViewPager.getCurrentItem() + 1) % mViewPager.getAdapter().getCount(), true);
Run Code Online (Sandbox Code Playgroud)我已经尝试过这篇文章了,但是效果不好,因为当用户拖动到完成切换到另一个页面之前停止时它会出现同样的问题.
只有类似的解决方案可以使用单个ViewPager(此处),但我需要使用2个ViewPagers,每个都会影响另一个.
所以我自己尝试过:假设一个viewPager是"viewPager",另一个(应该跟随"viewPager")是"viewPager2",这就是我所做的:
viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
int lastPositionOffsetPixels=Integer.MIN_VALUE;
@Override
public void onPageScrolled(final int position, final float positionOffset, final int positionOffsetPixels) {
if (!viewPager2.isFakeDragging())
viewPager2.beginFakeDrag();
if(lastPositionOffsetPixels==Integer.MIN_VALUE) {
lastPositionOffsetPixels=positionOffsetPixels;
return;
}
viewPager2.fakeDragBy((lastPositionOffsetPixels - positionOffsetPixels) * viewPager2.getWidth() / viewPager.getWidth());
lastPositionOffsetPixels = positionOffsetPixels;
}
@Override
public void onPageSelected(final int position) {
if (viewPager2.isFakeDragging())
viewPager2.endFakeDrag();
viewPager2.setCurrentItem(position,true);
}
@Override
public void onPageScrollStateChanged(final …Run Code Online (Sandbox Code Playgroud) android ×10
animation ×1
filechannel ×1
inputstream ×1
mp4parser ×1
networking ×1
oneplusthree ×1
overscroll ×1
parallax ×1
scroll ×1
snapping ×1