Files
Android-pyApi/android_pyapi/android/media_tv.py
T
shuiyu1123 506f9ac725 feat: 新增 42 个 Android API 模块
新增模块覆盖:
系统层 (14): system, security, print, opengl, renderscript, transition,
test, service_notification, service_controls, service_quicksettings,
service_wallpaper, service_autofill, service_dreams, service_vr

应用层 (13): app_admin, app_backup, app_job, app_usage, app_role,
app_people, appwidget, companion, credentials, mtp, sip, telecom, speech

硬件媒体层 (15): hardware_display, hardware_fingerprint, hardware_usb,
hardware_input, media_audiofx, media_browse, media_session, media_tv,
media_midi, media_projection, uwb, se, view_autofill, view_textclassifier,
view_translation

总计 94 个模块,75,342 行代码
2026-06-24 12:00:28 +00:00

359 lines
11 KiB
Python

"""
Android media.tv 组件 — TvInputManager, TvInputInfo, TvInputService 等
方法签名完全对齐 Android SDK
"""
from typing import Any, Callable, Dict, List, Optional
from .._core import Stub, AndroidOnlyError
# ═══════════════════════════════════════════════════════════════
# TvInputManager
# ═══════════════════════════════════════════════════════════════
class TvInputManager(Stub):
"""TvInputManager — 电视输入管理器"""
ACTION_VIEW_RECORDING_SCHEDULES = "android.tv.action.VIEW_RECORDING_SCHEDULES"
ACTION_WATCH_NEXT = "android.tv.action.WATCH_NEXT"
TIME_SHIFT_STATUS_AVAILABLE = 0
TIME_SHIFT_STATUS_UNAVAILABLE = 1
TIME_SHIFT_STATUS_UNKNOWN = 2
TIME_SHIFT_STATUS_UNSUPPORTED = 3
VIDEO_UNAVAILABLE_REASON_AUDIO_ONLY = 8
VIDEO_UNAVAILABLE_REASON_BUFFERING = 3
VIDEO_UNAVAILABLE_REASON_CAS = 7
VIDEO_UNAVAILABLE_REASON_INSUFFICIENT_RESOURCE = 5
VIDEO_UNAVAILABLE_REASON_NOT_CONNECTED = 6
VIDEO_UNAVAILABLE_REASON_PREEMPTED = 4
VIDEO_UNAVAILABLE_REASON_TUNING = 1
VIDEO_UNAVAILABLE_REASON_UNKNOWN = 0
VIDEO_UNAVAILABLE_REASON_WEAK_SIGNAL = 2
# ═══════════════════════════════════════════════════════════
# TvInputCallback
# ═══════════════════════════════════════════════════════════
class TvInputCallback(Stub):
"""TvInputManager.TvInputCallback — 电视输入回调"""
def onInputAdded(self, inputId: str):
pass
def onInputRemoved(self, inputId: str):
pass
def onInputChanged(self, inputId: str):
pass
def onInputStateChanged(self, inputId: str, state: int):
pass
def onTvInputInfoUpdated(self, inputInfo: "TvInputInfo"):
pass
def __init__(self):
super().__init__()
self._inputs: Dict[str, TvInputInfo] = {}
self._callbacks: Dict[int, TvInputManager.TvInputCallback] = {}
def getTvInputList(self) -> List["TvInputInfo"]:
return list(self._inputs.values())
def getTvInputInfo(self, inputId: str) -> Optional["TvInputInfo"]:
return self._inputs.get(inputId)
def getCurrentTvInputInfo(self) -> Optional["TvInputInfo"]:
for inp in self._inputs.values():
return inp
return None
def updateTvInputInfo(self, inputInfo: "TvInputInfo"):
if inputInfo:
self._inputs[inputInfo.getId()] = inputInfo
def registerCallback(self, callback: TvInputCallback, handler: Any = None):
lid = id(callback)
self._callbacks[lid] = callback
def unregisterCallback(self, callback: TvInputCallback):
lid = id(callback)
self._callbacks.pop(lid, None)
def createRecordingSession(self, recordingService: str, inputId: str):
raise AndroidOnlyError("TvInputManager.createRecordingSession() is not available on desktop")
def sendTvInputNotifyIntent(self, intent: Any, inputId: str):
pass
def isParentalControlsEnabled(self) -> bool:
return False
def isRatingBlocked(self, rating: str) -> bool:
return False
def getBlockedRatings(self) -> List[str]:
return []
def getAvailableTvInputs(self) -> List[str]:
return list(self._inputs.keys())
def getTvContentRatingSystems(self) -> List[str]:
return ["US_TV", "US_MOVIE"]
# ═══════════════════════════════════════════════════════════════
# TvInputInfo
# ═══════════════════════════════════════════════════════════════
class TvInputInfo(Stub):
"""TvInputInfo — 电视输入信息"""
TYPE_COMPONENT = 1005
TYPE_COMPOSITE = 1004
TYPE_HDMI = 1007
TYPE_OTHER = 1001
TYPE_SCART = 1003
TYPE_SVIDEO = 1006
TYPE_TUNER = 0
TYPE_DISPLAY_LINK = 1008
TYPE_VGA = 1002
def __init__(self, id: str = "", serviceInfo: Any = None,
parentId: str = "", type_: int = TYPE_TUNER,
hdmiDeviceInfo: Any = None,
isHidden: bool = False, canRecord: bool = False,
canPauseRecording: bool = False):
super().__init__()
self._id = id
self._service_info = serviceInfo
self._parent_id = parentId
self._type = type_
self._hdmi_device_info = hdmiDeviceInfo
self._is_hidden = isHidden
self._can_record = canRecord
self._can_pause_recording = canPauseRecording
def getId(self) -> str:
return self._id
def getServiceInfo(self) -> Any:
return self._service_info
def getParentId(self) -> str:
return self._parent_id
def getType(self) -> int:
return self._type
def getHdmiDeviceInfo(self) -> Any:
return self._hdmi_device_info
def loadIcon(self, context: Any) -> Any:
return None
def loadLogo(self, context: Any) -> Any:
return None
def createIntentForSetupScreen(self) -> Any:
return None
def isHidden(self) -> bool:
return self._is_hidden
def canRecord(self) -> bool:
return self._can_record
def canPauseRecording(self) -> bool:
return self._can_pause_recording
def toString(self) -> str:
type_names = {
TvInputInfo.TYPE_TUNER: "TUNER",
TvInputInfo.TYPE_HDMI: "HDMI",
TvInputInfo.TYPE_COMPOSITE: "COMPOSITE",
TvInputInfo.TYPE_COMPONENT: "COMPONENT",
}
return f"TvInputInfo(id={self._id}, type={type_names.get(self._type, str(self._type))})"
# ═══════════════════════════════════════════════════════════════
# TvInputService
# ═══════════════════════════════════════════════════════════════
class TvInputService(Stub):
"""TvInputService — 电视输入服务"""
RECORDING_ERROR_RECORDING_LOST = 0
RECORDING_ERROR_TIMEOUT = 1
RECORDING_ERROR_OTHER = 2
# ═══════════════════════════════════════════════════════════
# Session
# ═══════════════════════════════════════════════════════════
class Session(Stub):
"""TvInputService.Session — 电视会话"""
def __init__(self):
super().__init__()
self._main = False
self._stream_volume = 1.0
self._caption_enabled = False
def onSetSurface(self, surface: Any) -> bool:
return True
def onSurfaceChanged(self, format: int, width: int, height: int):
pass
def onSurfaceReleased(self):
pass
def onAppPrivateCommand(self, action: str, data: Any):
pass
def onCreateOverlayView(self) -> Any:
return None
def onRelayoutContent(self):
pass
def onSetCaptionEnabled(self, enabled: bool):
self._caption_enabled = enabled
def onSetStreamVolume(self, volume: float):
self._stream_volume = volume
def onTimeShiftSetCurrentPositionRequest(self, positionMs: int):
pass
def notifyTimeShiftStatusChanged(self, status: int):
pass
def scheduleOverlayView(self, view: Any):
pass
def timeShiftPlay(self, uri: str):
pass
def timeShiftPause(self):
pass
def timeShiftResume(self):
pass
def timeShiftSeekTo(self, positionMs: int):
pass
def timeShiftSetPlaybackParams(self, params: Any):
pass
def timeShiftEnablePositionTracking(self, enable: bool):
pass
def notifyVideoAvailable(self):
pass
def notifyVideoUnavailable(self, reason: int):
pass
def notifySessionEvent(self, eventType: str, eventArgs: Any):
pass
def notifyTracksChanged(self, tracks: List[Any]):
pass
def notifyTrackSelected(self, type_: str, trackId: str):
pass
def notifyContentAllowed(self):
pass
def notifyContentBlocked(self, rating: str):
pass
def setMain(self, main: bool):
self._main = main
def setStreamVolume(self, volume: float):
self._stream_volume = volume
def __init__(self):
super().__init__()
self._sessions: List[TvInputService.Session] = []
def onCreateSession(self, inputId: str) -> Session:
session = TvInputService.Session()
self._sessions.append(session)
return session
def onSetupFinished(self, inputId: str):
pass
def sessionCreated(self, session: Session):
pass
def notifyHardwareFailed(self, deviceId: int):
pass
# ═══════════════════════════════════════════════════════════════
# TvRecordingClient / TvRecordingService (stubs)
# ═══════════════════════════════════════════════════════════════
class TvRecordingClient(Stub):
"""TvRecordingClient — 电视录制客户端"""
def __init__(self):
super().__init__()
def startRecording(self, uri: str):
pass
def stopRecording(self):
pass
def pauseRecording(self):
pass
def resumeRecording(self):
pass
def release(self):
pass
class TvRecordingService(Stub):
"""TvRecordingService — 电视录制服务"""
def __init__(self):
super().__init__()
def onStartRecording(self, inputId: str, sessionId: str):
pass
def onStopRecording(self, sessionId: str):
pass
def onPauseRecording(self, sessionId: str):
pass
def onResumeRecording(self, sessionId: str):
pass
# ═══════════════════════════════════════════════════════════════
# __all__
# ═══════════════════════════════════════════════════════════════
__all__ = [
"TvInputManager",
"TvInputInfo",
"TvInputService",
"TvRecordingClient",
"TvRecordingService",
]