commit
3e83bb0d95
|
@ -84,6 +84,7 @@ NewPipe は複数のサービスに対応しています。[ドキュメント](
|
||||||
* SoundCloud \[ベータ\]
|
* SoundCloud \[ベータ\]
|
||||||
* media.ccc.de \[ベータ\]
|
* media.ccc.de \[ベータ\]
|
||||||
* PeerTube インスタンス \[ベータ\]
|
* PeerTube インスタンス \[ベータ\]
|
||||||
|
* Bandcamp \[ベータ\]
|
||||||
|
|
||||||
<!-- Hidden span to keep old links compatible. -->
|
<!-- Hidden span to keep old links compatible. -->
|
||||||
<span id="updates"></span>
|
<span id="updates"></span>
|
||||||
|
|
|
@ -79,6 +79,7 @@ NewPipe는 여러가지 서비스를 지원합니다. 우리의 [문서](https:/
|
||||||
* SoundCloud \[beta\]
|
* SoundCloud \[beta\]
|
||||||
* media.ccc.de \[beta\]
|
* media.ccc.de \[beta\]
|
||||||
* PeerTube instances \[beta\]
|
* PeerTube instances \[beta\]
|
||||||
|
* Bandcamp \[beta\]
|
||||||
|
|
||||||
## Updates
|
## Updates
|
||||||
NewPipe 코드의 변경이 있을 때(기능 추가 또는 버그 수정으로 인해), 결국 릴리즈가 발생할 것입니다. 이것들의 형식은 x.xx.x 입니다.
|
NewPipe 코드의 변경이 있을 때(기능 추가 또는 버그 수정으로 인해), 결국 릴리즈가 발생할 것입니다. 이것들의 형식은 x.xx.x 입니다.
|
||||||
|
|
|
@ -81,6 +81,7 @@ NewPipe supports multiple services. Our [docs](https://teamnewpipe.github.io/doc
|
||||||
* SoundCloud \[beta\]
|
* SoundCloud \[beta\]
|
||||||
* media.ccc.de \[beta\]
|
* media.ccc.de \[beta\]
|
||||||
* PeerTube instances \[beta\]
|
* PeerTube instances \[beta\]
|
||||||
|
* Bandcamp \[beta\]
|
||||||
|
|
||||||
<!-- Hidden span to keep old links compatible. -->
|
<!-- Hidden span to keep old links compatible. -->
|
||||||
<span id="updates"></span>
|
<span id="updates"></span>
|
||||||
|
|
|
@ -79,6 +79,7 @@ O NewPipe suporta vários serviços. Nosso [documentação](https://teamnewpipe.
|
||||||
* SoundCloud \[beta\]
|
* SoundCloud \[beta\]
|
||||||
* media.ccc.de \[beta\]
|
* media.ccc.de \[beta\]
|
||||||
* PeerTube instances \[beta\]
|
* PeerTube instances \[beta\]
|
||||||
|
* Bandcamp \[beta\]
|
||||||
|
|
||||||
## Atualizações
|
## Atualizações
|
||||||
Quando uma alteração no código NewPipe (devido à adição de recursos ou fixação de bugs), eventualmente ocorrerá uma versão. Estes estão no formato x.xx.x . A fim de obter esta nova versão, você pode:
|
Quando uma alteração no código NewPipe (devido à adição de recursos ou fixação de bugs), eventualmente ocorrerá uma versão. Estes estão no formato x.xx.x . A fim de obter esta nova versão, você pode:
|
||||||
|
|
|
@ -81,6 +81,7 @@ NewPipe suportă servicii multiple. [Documentele](https://teamnewpipe.github.io/
|
||||||
* SoundCloud \[beta\]
|
* SoundCloud \[beta\]
|
||||||
* media.ccc.de \[beta\]
|
* media.ccc.de \[beta\]
|
||||||
* Instanţe PeerTube \[beta\]
|
* Instanţe PeerTube \[beta\]
|
||||||
|
* Bandcamp \[beta\]
|
||||||
|
|
||||||
<!-- Hidden span to keep old links compatible. -->
|
<!-- Hidden span to keep old links compatible. -->
|
||||||
<span id="updates"></span>
|
<span id="updates"></span>
|
||||||
|
|
|
@ -79,6 +79,7 @@ NewPipe wuxuu taageeraa adeegyo badan. [warqadan](https://teamnewpipe.github.io/
|
||||||
* SoundCloud \[tijaabo\]
|
* SoundCloud \[tijaabo\]
|
||||||
* media.ccc.de \[tijaabo\]
|
* media.ccc.de \[tijaabo\]
|
||||||
* PeerTube instances \[tijaabo\]
|
* PeerTube instances \[tijaabo\]
|
||||||
|
* Bandcamp \[tijaabo\]
|
||||||
|
|
||||||
## Kushubida iyo cusboonaysiinta
|
## Kushubida iyo cusboonaysiinta
|
||||||
Marka koodhka NewPipe isbadal ku dhaco (wax cusub oo lagusoo kordhiyay ama cilad bixin), ugu dambayn waxaa lasii daayaa mid cusub (Siidayn). Siidaynta qaabkeedu waa x.xx.x . Si aad midka cusub u hesho, waxaad samayn kartaa:
|
Marka koodhka NewPipe isbadal ku dhaco (wax cusub oo lagusoo kordhiyay ama cilad bixin), ugu dambayn waxaa lasii daayaa mid cusub (Siidayn). Siidaynta qaabkeedu waa x.xx.x . Si aad midka cusub u hesho, waxaad samayn kartaa:
|
||||||
|
|
|
@ -180,7 +180,7 @@ dependencies {
|
||||||
|
|
||||||
// NewPipe dependencies
|
// NewPipe dependencies
|
||||||
// You can use a local version by uncommenting a few lines in settings.gradle
|
// You can use a local version by uncommenting a few lines in settings.gradle
|
||||||
implementation "com.github.TeamNewPipe:NewPipeExtractor:7e6f464407fc1a2c8fb0886d294093526a6ef0f1"
|
implementation 'com.github.TeamNewPipe:NewPipeExtractor:def745b801b2ef35c1a0fee1be950331ca6a0cd2'
|
||||||
implementation "com.github.TeamNewPipe:nanojson:1d9e1aea9049fc9f85e68b43ba39fe7be1c1f751"
|
implementation "com.github.TeamNewPipe:nanojson:1d9e1aea9049fc9f85e68b43ba39fe7be1c1f751"
|
||||||
|
|
||||||
implementation "org.jsoup:jsoup:1.13.1"
|
implementation "org.jsoup:jsoup:1.13.1"
|
||||||
|
|
|
@ -317,6 +317,22 @@
|
||||||
<data android:pathPrefix="/accounts/" />
|
<data android:pathPrefix="/accounts/" />
|
||||||
<data android:pathPrefix="/video-channels/" />
|
<data android:pathPrefix="/video-channels/" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
|
|
||||||
|
<!-- Bandcamp filter -->
|
||||||
|
<intent-filter>
|
||||||
|
<action android:name="android.intent.action.VIEW"/>
|
||||||
|
<action android:name="android.media.action.MEDIA_PLAY_FROM_SEARCH"/>
|
||||||
|
<action android:name="android.nfc.action.NDEF_DISCOVERED"/>
|
||||||
|
|
||||||
|
<category android:name="android.intent.category.DEFAULT"/>
|
||||||
|
<category android:name="android.intent.category.BROWSABLE"/>
|
||||||
|
|
||||||
|
<data android:scheme="http"/>
|
||||||
|
<data android:scheme="https"/>
|
||||||
|
<data android:host="bandcamp.com"/>
|
||||||
|
<data android:host="*.bandcamp.com"/>
|
||||||
|
<data android:pathPrefix="/"/>
|
||||||
|
</intent-filter>
|
||||||
</activity>
|
</activity>
|
||||||
<service
|
<service
|
||||||
android:name=".RouterActivity$FetcherService"
|
android:name=".RouterActivity$FetcherService"
|
||||||
|
|
|
@ -62,6 +62,7 @@ import org.schabi.newpipe.error.ReCaptchaActivity;
|
||||||
import org.schabi.newpipe.error.UserAction;
|
import org.schabi.newpipe.error.UserAction;
|
||||||
import org.schabi.newpipe.extractor.InfoItem;
|
import org.schabi.newpipe.extractor.InfoItem;
|
||||||
import org.schabi.newpipe.extractor.NewPipe;
|
import org.schabi.newpipe.extractor.NewPipe;
|
||||||
|
import org.schabi.newpipe.extractor.exceptions.ContentNotSupportedException;
|
||||||
import org.schabi.newpipe.extractor.exceptions.ExtractionException;
|
import org.schabi.newpipe.extractor.exceptions.ExtractionException;
|
||||||
import org.schabi.newpipe.extractor.stream.AudioStream;
|
import org.schabi.newpipe.extractor.stream.AudioStream;
|
||||||
import org.schabi.newpipe.extractor.stream.Stream;
|
import org.schabi.newpipe.extractor.stream.Stream;
|
||||||
|
@ -1546,10 +1547,21 @@ public final class VideoDetailFragment
|
||||||
updateOverlayData(info.getName(), info.getUploaderName(), info.getThumbnailUrl());
|
updateOverlayData(info.getName(), info.getUploaderName(), info.getThumbnailUrl());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!info.getErrors().isEmpty()) {
|
||||||
|
// Bandcamp fan pages are not yet supported and thus a ContentNotAvailableException is
|
||||||
|
// thrown. This is not an error and thus should not be shown to the user.
|
||||||
|
for (final Throwable throwable : info.getErrors()) {
|
||||||
|
if (throwable instanceof ContentNotSupportedException
|
||||||
|
&& "Fan pages are not supported".equals(throwable.getMessage())) {
|
||||||
|
info.getErrors().remove(throwable);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (!info.getErrors().isEmpty()) {
|
if (!info.getErrors().isEmpty()) {
|
||||||
showSnackBarError(new ErrorInfo(info.getErrors(),
|
showSnackBarError(new ErrorInfo(info.getErrors(),
|
||||||
UserAction.REQUESTED_STREAM, info.getUrl(), info));
|
UserAction.REQUESTED_STREAM, info.getUrl(), info));
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
binding.detailControlsDownload.setVisibility(info.getStreamType() == StreamType.LIVE_STREAM
|
binding.detailControlsDownload.setVisibility(info.getStreamType() == StreamType.LIVE_STREAM
|
||||||
|| info.getStreamType() == StreamType.AUDIO_LIVE_STREAM ? View.GONE : View.VISIBLE);
|
|| info.getStreamType() == StreamType.AUDIO_LIVE_STREAM ? View.GONE : View.VISIBLE);
|
||||||
|
|
|
@ -1129,6 +1129,12 @@ public final class Player implements
|
||||||
// Close it because when changing orientation from portrait
|
// Close it because when changing orientation from portrait
|
||||||
// (in fullscreen mode) the size of queue layout can be larger than the screen size
|
// (in fullscreen mode) the size of queue layout can be larger than the screen size
|
||||||
closeItemsList();
|
closeItemsList();
|
||||||
|
// When the orientation changed, the screen height might be smaller.
|
||||||
|
// If the end screen thumbnail is not re-scaled,
|
||||||
|
// it can be larger than the current screen height
|
||||||
|
// and thus enlarging the whole player.
|
||||||
|
// This causes the seekbar to be ouf the visible area.
|
||||||
|
updateEndScreenThumbnail();
|
||||||
break;
|
break;
|
||||||
case Intent.ACTION_SCREEN_ON:
|
case Intent.ACTION_SCREEN_ON:
|
||||||
// Interrupt playback only when screen turns on
|
// Interrupt playback only when screen turns on
|
||||||
|
@ -1187,6 +1193,78 @@ public final class Player implements
|
||||||
.loadImage(url, ImageDisplayConstants.DISPLAY_THUMBNAIL_OPTIONS, this);
|
.loadImage(url, ImageDisplayConstants.DISPLAY_THUMBNAIL_OPTIONS, this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Scale the player audio / end screen thumbnail down if necessary.
|
||||||
|
* <p>
|
||||||
|
* This is necessary when the thumbnail's height is larger than the device's height
|
||||||
|
* and thus is enlarging the player's height
|
||||||
|
* causing the bottom playback controls to be out of the visible screen.
|
||||||
|
* </p>
|
||||||
|
*/
|
||||||
|
public void updateEndScreenThumbnail() {
|
||||||
|
if (currentThumbnail == null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
final float endScreenHeight = calculateMaxEndScreenThumbnailHeight();
|
||||||
|
|
||||||
|
final Bitmap endScreenBitmap = Bitmap.createScaledBitmap(
|
||||||
|
currentThumbnail,
|
||||||
|
(int) (currentThumbnail.getWidth()
|
||||||
|
/ (currentThumbnail.getHeight() / endScreenHeight)),
|
||||||
|
(int) endScreenHeight,
|
||||||
|
true);
|
||||||
|
|
||||||
|
if (DEBUG) {
|
||||||
|
Log.d(TAG, "Thumbnail - updateEndScreenThumbnail() called with: "
|
||||||
|
+ "currentThumbnail = [" + currentThumbnail + "], "
|
||||||
|
+ currentThumbnail.getWidth() + "x" + currentThumbnail.getHeight()
|
||||||
|
+ ", scaled end screen height = " + endScreenHeight
|
||||||
|
+ ", scaled end screen width = " + endScreenBitmap.getWidth());
|
||||||
|
}
|
||||||
|
|
||||||
|
binding.endScreen.setImageBitmap(endScreenBitmap);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Calculate the maximum allowed height for the {@link R.id.endScreen}
|
||||||
|
* to prevent it from enlarging the player.
|
||||||
|
* <p>
|
||||||
|
* The calculating follows these rules:
|
||||||
|
* <ul>
|
||||||
|
* <li>
|
||||||
|
* Show at least stream title and content creator on TVs and tablets
|
||||||
|
* when in landscape (always the case for TVs) and not in fullscreen mode.
|
||||||
|
* This requires to have at least <code>85dp</code> free space for {@link R.id.detail_root}
|
||||||
|
* and additional space for the stream title text size
|
||||||
|
* ({@link R.id.detail_title_root_layout}).
|
||||||
|
* The text size is <code>15sp</code> on tablets and <code>16sp</code> on TVs,
|
||||||
|
* see {@link R.id.titleTextView}.
|
||||||
|
* </li>
|
||||||
|
* <li>
|
||||||
|
* Otherwise, the max thumbnail height is the screen height.
|
||||||
|
* </li>
|
||||||
|
* </ul>
|
||||||
|
*
|
||||||
|
* @return the maximum height for the end screen thumbnail
|
||||||
|
*/
|
||||||
|
private float calculateMaxEndScreenThumbnailHeight() {
|
||||||
|
// ensure that screenHeight is initialized and thus not 0
|
||||||
|
updateScreenSize();
|
||||||
|
|
||||||
|
if (DeviceUtils.isTv(context) && !isFullscreen) {
|
||||||
|
final int videoInfoHeight =
|
||||||
|
DeviceUtils.dpToPx(85, context) + DeviceUtils.spToPx(16, context);
|
||||||
|
return Math.min(currentThumbnail.getHeight(), screenHeight - videoInfoHeight);
|
||||||
|
} else if (DeviceUtils.isTablet(context) && service.isLandscape() && !isFullscreen) {
|
||||||
|
final int videoInfoHeight =
|
||||||
|
DeviceUtils.dpToPx(85, context) + DeviceUtils.spToPx(15, context);
|
||||||
|
return Math.min(currentThumbnail.getHeight(), screenHeight - videoInfoHeight);
|
||||||
|
} else { // fullscreen player: max height is the device height
|
||||||
|
return Math.min(currentThumbnail.getHeight(), screenHeight);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onLoadingStarted(final String imageUri, final View view) {
|
public void onLoadingStarted(final String imageUri, final View view) {
|
||||||
if (DEBUG) {
|
if (DEBUG) {
|
||||||
|
@ -1207,23 +1285,29 @@ public final class Player implements
|
||||||
@Override
|
@Override
|
||||||
public void onLoadingComplete(final String imageUri, final View view,
|
public void onLoadingComplete(final String imageUri, final View view,
|
||||||
final Bitmap loadedImage) {
|
final Bitmap loadedImage) {
|
||||||
final float width = Math.min(
|
// scale down the notification thumbnail for performance
|
||||||
|
final float notificationThumbnailWidth = Math.min(
|
||||||
context.getResources().getDimension(R.dimen.player_notification_thumbnail_width),
|
context.getResources().getDimension(R.dimen.player_notification_thumbnail_width),
|
||||||
loadedImage.getWidth());
|
loadedImage.getWidth());
|
||||||
|
currentThumbnail = Bitmap.createScaledBitmap(
|
||||||
|
loadedImage,
|
||||||
|
(int) notificationThumbnailWidth,
|
||||||
|
(int) (loadedImage.getHeight()
|
||||||
|
/ (loadedImage.getWidth() / notificationThumbnailWidth)),
|
||||||
|
true);
|
||||||
|
|
||||||
if (DEBUG) {
|
if (DEBUG) {
|
||||||
Log.d(TAG, "Thumbnail - onLoadingComplete() called with: "
|
Log.d(TAG, "Thumbnail - onLoadingComplete() called with: "
|
||||||
+ "imageUri = [" + imageUri + "], view = [" + view + "], "
|
+ "imageUri = [" + imageUri + "], view = [" + view + "], "
|
||||||
+ "loadedImage = [" + loadedImage + "], "
|
+ "loadedImage = [" + loadedImage + "], "
|
||||||
+ loadedImage.getWidth() + "x" + loadedImage.getHeight()
|
+ loadedImage.getWidth() + "x" + loadedImage.getHeight()
|
||||||
+ ", scaled width = " + width);
|
+ ", scaled notification width = " + notificationThumbnailWidth);
|
||||||
}
|
}
|
||||||
|
|
||||||
currentThumbnail = Bitmap.createScaledBitmap(loadedImage,
|
|
||||||
(int) width,
|
|
||||||
(int) (loadedImage.getHeight() / (loadedImage.getWidth() / width)), true);
|
|
||||||
binding.endScreen.setImageBitmap(loadedImage);
|
|
||||||
NotificationUtil.getInstance().createNotificationIfNeededAndUpdate(this, false);
|
NotificationUtil.getInstance().createNotificationIfNeededAndUpdate(this, false);
|
||||||
|
|
||||||
|
// there is a new thumbnail, thus the end screen thumbnail needs to be changed, too.
|
||||||
|
updateEndScreenThumbnail();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -6,8 +6,10 @@ import android.content.pm.PackageManager;
|
||||||
import android.content.res.Configuration;
|
import android.content.res.Configuration;
|
||||||
import android.os.BatteryManager;
|
import android.os.BatteryManager;
|
||||||
import android.os.Build;
|
import android.os.Build;
|
||||||
|
import android.util.TypedValue;
|
||||||
import android.view.KeyEvent;
|
import android.view.KeyEvent;
|
||||||
|
|
||||||
|
import androidx.annotation.Dimension;
|
||||||
import androidx.annotation.NonNull;
|
import androidx.annotation.NonNull;
|
||||||
import androidx.core.content.ContextCompat;
|
import androidx.core.content.ContextCompat;
|
||||||
|
|
||||||
|
@ -70,4 +72,20 @@ public final class DeviceUtils {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static int dpToPx(@Dimension(unit = Dimension.DP) final int dp,
|
||||||
|
@NonNull final Context context) {
|
||||||
|
return (int) TypedValue.applyDimension(
|
||||||
|
TypedValue.COMPLEX_UNIT_DIP,
|
||||||
|
dp,
|
||||||
|
context.getResources().getDisplayMetrics());
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int spToPx(@Dimension(unit = Dimension.SP) final int sp,
|
||||||
|
@NonNull final Context context) {
|
||||||
|
return (int) TypedValue.applyDimension(
|
||||||
|
TypedValue.COMPLEX_UNIT_SP,
|
||||||
|
sp,
|
||||||
|
context.getResources().getDisplayMetrics());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -48,6 +48,10 @@ public final class KioskTranslator {
|
||||||
return c.getString(R.string.recent);
|
return c.getString(R.string.recent);
|
||||||
case "live":
|
case "live":
|
||||||
return c.getString(R.string.duration_live);
|
return c.getString(R.string.duration_live);
|
||||||
|
case "Featured":
|
||||||
|
return c.getString(R.string.featured);
|
||||||
|
case "Radio":
|
||||||
|
return c.getString(R.string.radio);
|
||||||
default:
|
default:
|
||||||
return kioskId;
|
return kioskId;
|
||||||
}
|
}
|
||||||
|
@ -69,6 +73,10 @@ public final class KioskTranslator {
|
||||||
return ThemeHelper.resolveResourceIdFromAttr(c, R.attr.ic_thumb_up);
|
return ThemeHelper.resolveResourceIdFromAttr(c, R.attr.ic_thumb_up);
|
||||||
case "live":
|
case "live":
|
||||||
return ThemeHelper.resolveResourceIdFromAttr(c, R.attr.ic_live_tv);
|
return ThemeHelper.resolveResourceIdFromAttr(c, R.attr.ic_live_tv);
|
||||||
|
case "Featured":
|
||||||
|
return ThemeHelper.resolveResourceIdFromAttr(c, R.attr.ic_stars);
|
||||||
|
case "Radio":
|
||||||
|
return ThemeHelper.resolveResourceIdFromAttr(c, R.attr.ic_radio);
|
||||||
default:
|
default:
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
@ -38,6 +38,8 @@ public final class ServiceHelper {
|
||||||
return R.drawable.place_holder_gadse;
|
return R.drawable.place_holder_gadse;
|
||||||
case 3:
|
case 3:
|
||||||
return R.drawable.place_holder_peertube;
|
return R.drawable.place_holder_peertube;
|
||||||
|
case 4:
|
||||||
|
return R.drawable.place_holder_bandcamp;
|
||||||
default:
|
default:
|
||||||
return R.drawable.place_holder_circle;
|
return R.drawable.place_holder_circle;
|
||||||
}
|
}
|
||||||
|
|
Binary file not shown.
After Width: | Height: | Size: 6.7 KiB |
|
@ -44,4 +44,13 @@
|
||||||
<color name="dark_media_ccc_accent_color">#FFFFFF</color>
|
<color name="dark_media_ccc_accent_color">#FFFFFF</color>
|
||||||
<color name="dark_media_ccc_statusbar_color">#9e9e9e</color>
|
<color name="dark_media_ccc_statusbar_color">#9e9e9e</color>
|
||||||
|
|
||||||
|
<!-- Bandcamp -->
|
||||||
|
<color name="light_bandcamp_primary_color">#17a0c4</color>
|
||||||
|
<color name="light_bandcamp_accent_color">#000000</color>
|
||||||
|
<color name="light_bandcamp_statusbar_color">#17a0c4</color>
|
||||||
|
|
||||||
|
<color name="dark_bandcamp_primary_color">#17a0c4</color>
|
||||||
|
<color name="dark_bandcamp_accent_color">#FFFFFF</color>
|
||||||
|
<color name="dark_bandcamp_statusbar_color">#17a0c4</color>
|
||||||
|
|
||||||
</resources>
|
</resources>
|
|
@ -707,4 +707,6 @@
|
||||||
<string name="private_content">This content is private, so it cannot be streamed or downloaded by NewPipe.</string>
|
<string name="private_content">This content is private, so it cannot be streamed or downloaded by NewPipe.</string>
|
||||||
<string name="youtube_music_premium_content">This video is available only to YouTube Music Premium members, so it cannot be streamed or downloaded by NewPipe.</string>
|
<string name="youtube_music_premium_content">This video is available only to YouTube Music Premium members, so it cannot be streamed or downloaded by NewPipe.</string>
|
||||||
<string name="paid_content">This content is only available to users who have paid, so it cannot be streamed or downloaded by NewPipe.</string>
|
<string name="paid_content">This content is only available to users who have paid, so it cannot be streamed or downloaded by NewPipe.</string>
|
||||||
|
<string name="featured">Featured</string>
|
||||||
|
<string name="radio">Radio</string>
|
||||||
</resources>
|
</resources>
|
||||||
|
|
|
@ -70,4 +70,23 @@
|
||||||
<item name="colorAccent">@color/dark_media_ccc_accent_color</item>
|
<item name="colorAccent">@color/dark_media_ccc_accent_color</item>
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
|
<!-- Bandcamp -->
|
||||||
|
<style name="LightTheme.Bandcamp" parent="LightTheme">
|
||||||
|
<item name="colorPrimary">@color/light_bandcamp_primary_color</item>
|
||||||
|
<item name="colorPrimaryDark">@color/light_bandcamp_statusbar_color</item>
|
||||||
|
<item name="colorAccent">@color/light_bandcamp_accent_color</item>
|
||||||
|
</style>
|
||||||
|
|
||||||
|
<style name="DarkTheme.Bandcamp" parent="DarkTheme">
|
||||||
|
<item name="colorPrimary">@color/dark_bandcamp_primary_color</item>
|
||||||
|
<item name="colorPrimaryDark">@color/dark_bandcamp_statusbar_color</item>
|
||||||
|
<item name="colorAccent">@color/dark_bandcamp_accent_color</item>
|
||||||
|
</style>
|
||||||
|
|
||||||
|
<style name="BlackTheme.Bandcamp" parent="BlackTheme">
|
||||||
|
<item name="colorPrimary">@color/dark_bandcamp_primary_color</item>
|
||||||
|
<item name="colorPrimaryDark">@color/dark_bandcamp_statusbar_color</item>
|
||||||
|
<item name="colorAccent">@color/dark_bandcamp_accent_color</item>
|
||||||
|
</style>
|
||||||
|
|
||||||
</resources>
|
</resources>
|
||||||
|
|
Loading…
Reference in New Issue