TA的每日心情 | 开心 2019-9-4 10:12 |
---|
签到天数: 1 天 [LV.1]初来乍到
|
本帖最后由 jiaqiangmit2 于 2019-8-2 21:30 编辑
! u/ p: c3 V/ q
) i* t- \2 f& T) u: m. o" o+ R各位大神
' a K9 l% {3 p6 v$ ~/ ^我在anki里已经实现提取LDOCE6真人朗读例句的制卡。现在希望能将音频文件单独放手机,睡觉和开车等时间听。问题来了:anki对媒体文件的命名是以类似于HAsh方式“乱码”命名的,从媒体文件夹里复制出来,所有的例句和单词的朗读时打乱的。能否实现:单词以其拼写命名(example.mp3),对应的几个例句音频以单词拼写加后缀的方式命名,这样,放在手机里,单词和对应例句就可以一起读了。1 g+ V* M, ^6 b% g) k
4 Q K( a2 Z3 m4 |4 m V+ A
+ a+ n- C6 L& h" T* ]! j' A5 G如图,文件名是“l乱码”的
8 R8 P& {# M/ z3 {" c4 d+ T8 v无法上任附件,名字是这样的:
" O" l' |+ S4 v; V/ B- M [sound:-ldoce6-b0ab2fba-11b6ffb4-d84db123-b00153f3-9971952a.mp3]
* H5 D ~' G# ^& i& M/ M2 u1 \9 @' \$ }+ f- k: M) b- p
对应 脚本
# w- V4 O) q% _0 ]' @
! r) B* j [0 Y4 t------------------------------
6 q9 F/ R: R0 X" z
/ l5 w! A5 ~5 Q. D
! @, ?1 n6 b: }/ _. K- b#-*- coding:utf-8 -*-1 D9 W& r9 z9 y$ S5 U2 p
import os
3 O$ g, W( P- limport re; ~/ ^% A& F9 t6 c! V9 |2 I
import random, n1 D" J, N$ P$ ~4 m
from ..base import *
- C5 ?! G( i. M' `- a
8 l' o$ y4 v B7 F
( B4 W- F1 R# M Q' CVOICE_PATTERN = r'<a href="sound://([\w/]+\w*\.mp3)"><img src="img/spkr_%s.png"></a>'
: f* S0 n0 B% `, H$ E, P1 b0 ~' h6 nVOICE_PATTERN_WQ = r'<span class="%s"><a href="sound://([\w/]+\w*\.mp3)">(.*?)</span %s>') {6 c/ e! o( z: C7 r
MAPPINGS = [- I3 z' P0 h$ {
['br', [re.compile(VOICE_PATTERN % r'r'), re.compile(VOICE_PATTERN_WQ % (r'brevoice', r'brevoice'))]],
3 L, ]- S6 `- d$ J ['us', [re.compile(VOICE_PATTERN % r'b'), re.compile(VOICE_PATTERN_WQ % (r'amevoice', r'amevoice'))]]" T7 [ E0 K6 u2 c1 z3 ~; o9 D3 j
]
0 p! x5 O* ^6 G& E5 Q' Y/ h( Q; cLANG_TO_REGEXPS = {lang: regexps for lang, regexps in MAPPINGS}
% [: g1 e8 x+ Q1 n" i; ]DICT_PATH =u'E:\Anki\Dick\L6mp3.mdx'5 Q6 h6 Z* e" q' Y
( {% u6 m) z+ \
2 t! {2 g' g, b@register([u'本地词典-LDOCE6', u'MDX-LDOCE6'])
, ?8 y4 L0 R5 z# Mclass Ldoce6(MdxService):5 T* D; ^4 Z- T& s5 b$ l: o; S8 Q
& m3 T/ W$ u/ S& o def __init__(self):( {8 l$ c& s) [
dict_path = DICT_PATH6 a& W" N0 E, v6 {
# if DICT_PATH is a path, stop auto detect
2 V$ x0 Y4 I6 I2 e: y; K1 P( i if not dict_path:% V3 a+ N8 ` n- }0 N6 t& U
from ...service import service_manager, service_pool5 `5 i$ w: H* \ P9 W
for clazz in service_manager.mdx_services:
7 x9 a1 ~, o3 X: L, o service = service_pool.get(clazz.__unique__)- N) y1 R) s3 J. e% q0 K
title = service.builder._title if service and service.support else u''
" f9 s4 V/ {( k5 B! f service_pool.put(service)# \& K1 L1 [) \' u! C. S# J
if title.startswith(u'LDOCE6'):
+ e8 x- t5 Y. x1 A& v6 p" ` dict_path = service.dict_path* N/ q( I+ d+ E9 Q& T0 Z' P0 n7 w
break
+ Y% A& E9 O5 u% Y8 _- c super(Ldoce6, self).__init__(dict_path)* c/ w$ w+ E' _/ [. H1 s/ J! \
5 B# f" M/ D, o* c
@property; }) Y6 a# \5 S; D
def title(self):
: g" |, \! L7 e5 k0 D: u9 r/ Z return getattr(self, '__register_label__', self.unique)% d s; q& c0 w' C8 L% z7 ~
! P5 r1 }4 g& O8 c6 D4 N
@export('PHON'); f1 m J$ T2 A2 J
def fld_phonetic(self):/ J: m+ e$ f' `! p) f; `
html = self.get_html()
6 I, g! D% a8 Y& ]' ] m = re.search(r'<span class="pron">(.*?)</span>', html)
& {* Q1 s$ p0 o% X: m q if m:) c0 l, {2 J* O/ k. G
return m.groups()[0]2 o& J3 d( D0 ~+ a# ?
return ''
* v' {. g7 ~& {$ _
* J! [6 b3 H/ ^ def _fld_voice(self, html, voice):8 E3 a; x" W3 e0 k$ V- B$ F
"""获取发音字段"""- L; u$ q& w4 O8 D+ _; l
for regexp in LANG_TO_REGEXPS[voice]:- B6 p! j6 T6 ^9 C$ n
match = regexp.search(html)
2 X" T o. a8 F+ O if match:0 G4 m. ]( B) M! ]8 D* i
val = '/' + match.group(1)
6 }$ @3 R' @* s4 q2 t name = get_hex_name('mdx-'+self.unique.lower(), val, 'mp3'). I5 R( J+ h- @; L: H7 Q
name = self.save_file(val, name)& k6 W a7 q" }+ K [: P3 I! T
if name:8 q- u6 Y5 S* B% h3 @
return self.get_anki_label(name, 'audio')
& X# Z+ a9 `9 W5 A. M# ? return ''6 F2 I! z! L1 i& o( ]0 t3 b' J
: A/ H2 ?6 t# d- T5 Q @export('BRE_PRON')
* F/ @% C" h, A8 q0 K' A, O6 ` def fld_voicebre(self):7 @/ x' H, w- Q; R5 \+ U1 G+ q
return self._fld_voice(self.get_html(), 'br')/ |' B; e; J R; Z# _& D, Y" q, g
8 U& R+ H5 q( E# k9 J$ _$ S/ C @export('AME_PRON')
. X% }, b5 Q# O. ?: N& X+ D def fld_voiceame(self):
4 X6 w9 k0 ~ M$ C return self._fld_voice(self.get_html(), 'us')% `& u. P% J2 ?6 H5 @, x: Q
W: K8 K: ]; J3 f( P! V
def _fld_image(self, img):
H: l" @4 B5 u: Y$ m4 V val = '/' + img
" y; t( W3 K0 C, \8 a3 o # file extension isn't always jpg7 v6 N6 Z' ^+ G9 r( }
file_extension = os.path.splitext(img)[1][1:].strip().lower() E) j, A' R0 T
name = get_hex_name('mdx-'+self.unique.lower(), val, file_extension)
8 A( K6 f% N" S6 v* f" n3 e name = self.save_file(val, name)& }4 H6 j/ R: M* j) v$ c f3 z: N3 h" _: y
if name:
2 v, p/ w0 U- C2 d return self.get_anki_label(name, 'img')
/ |- R! X2 @" Z8 }2 T return ''
, A! W/ Q. o; V2 _, {. c0 U+ c$ H' T, r' Q+ I) W! {2 v
@export('IMAGE')6 C2 j8 f- g. h: \% H; r4 e7 u
def fld_image(self):
0 J/ p6 h$ T, }3 j' s$ ?0 z% f html = self.get_html()7 k% U. l, R0 q8 X% j( [
m = re.search(r'<span class="imgholder"><img src="(.*?)".*?></span>', html)
' Z4 N3 R) k2 s. G if m:
% V* g1 b2 j( W, L1 b7 { return self._fld_image(m.groups()[0])) d; ]. c0 V; q) w
return ''
0 i% D6 m' ` e/ T5 r7 u- h. a0 |' C3 r3 S! S5 M8 h
@export('EXAMPLE')' |; D& I7 X) ^& X2 d2 m
def fld_sentence(self):, r2 w# [/ a& h" i6 r+ L) D
return self._range_sentence([i for i in range(0, 100)])9 B) g% x# O7 M" S
& F5 ]# s+ y% h7 l, E. i, U7 h+ j def _fld_audio(self, audio):( B5 [( w2 P' @4 \' Q" S. f# Q2 t
name = get_hex_name('mdx-'+self.unique.lower(), audio, 'mp3'), ^6 z( B+ f3 ^! r
name = self.save_file(audio, name)
. {( o- z; B0 I if name:
) \) b. _- k; r0 C2 M$ B# S1 Y return self.get_anki_label(name, 'audio')5 a2 n; C2 z1 v
return ''% X+ }, k% o7 C+ D: I* ~' x
' D/ r% j2 D; h" y6 R/ d
@export([u'例句加音频', u'Examples with audios'])
+ c$ x! G# _; x def fld_sentence_audio(self):
$ E8 l# B8 Z! c) P% ?, k3 Y& C return self._range_sentence_audio([i for i in range(0, 100)])1 Q0 T& ]" K. E
. f& E- ^" {% @9 { `5 l1 m2 A0 g
@export('DEF')8 P/ w% r' p. P6 @- |7 b0 X
def fld_definate(self):
4 s8 I/ n8 v9 [ m = m = re.findall(r'<span class="def"\s*.*>\s*.*<\/span>', self.get_html())' ]4 G& @- |5 u- @, F
if m:% c# h* L) r& g `' e
soup = parse_html(m[0])
' S+ v# |) w1 W; @' T el_list = soup.findAll('span', {'class':'def'})
3 g7 {/ h7 J! A" `, x# u$ f" ]* K if el_list:& V$ ~. T& [! Y1 T: D$ ~. w! h0 B) O" ]
maps = [u''.join(str(content) for content in element.contents)
0 [0 @4 L' L# p/ h2 n; Z for element in el_list]6 o% B' h0 |# O) V
my_str = ''2 Q, N U: [( O. o; M+ `
for i_str in maps:
5 S- k5 z& R$ n( `+ P4 e) u my_str = my_str + '<li>' + i_str + '</li>') G3 {' I8 Q5 o; D
return self._css(my_str)
( [5 I+ V4 I$ O" Z return ''
& q9 ?# |3 J9 M4 ~
5 N" J2 Z' Q, C4 G @export([u'随机例句', u'Random example'])* V9 G" @. J2 C$ |, v4 `' m
def fld_random_sentence(self):
; H+ ]$ J( {+ b1 j return self._range_sentence()
T) r' g( }# K F6 e* y& X* L# g v; U: N
@export([u'首2个例句', u'First 2 examples'])
# ]/ A+ i& o+ A% } def fld_first2_sentence(self):7 Y/ ?4 I6 ?4 P& v1 H, L- G
return self._range_sentence([0, 1])
$ E( }$ J: n! o. \ 7 Q1 Q8 }1 h7 a) V) X3 n3 b
@export([u'随机例句加音频', u'Random example with audio'])
4 W/ r% a: K* q5 Z3 R# m S def fld_random_sentence_audio(self):
! G ?, D" c; J& h: t v6 [* ] return self._range_sentence_audio() \- E$ D$ x/ B5 o. K6 G! C
$ ?# ?) Q) Q. r- n
@export([u'首2个例句加音频', u'First 2 examples with audios'])+ Y- u7 L1 T! C+ u
def fld_first2_sentence_audio(self):
9 d7 |/ s' B( R/ x return self._range_sentence_audio([0, 1])9 J* @$ |3 j: d4 c% U/ U; H
% Z) w. I( ^8 r def _range_sentence(self, range_arr=None):! h' Q7 @7 T% @5 L
m = re.findall(r'<span class="example"\s*.*>\s*.*<\/span>', self.get_html())* g+ C7 }8 G9 w0 ^+ g" i. Q
if m:
/ m+ j$ C6 l! G" S, T, g. ?/ N soup = parse_html(m[0])
: y0 I) ^0 j/ D2 o el_list = soup.findAll('span', {'class':'example'})
3 H' O1 e3 u$ ?6 \: s2 A if el_list:
' k, A% c7 p& b% ? A0 M0 |. [ maps = [u''.join(str(content) for content in element.contents)
. M- j6 n5 ?* f1 e& p, ~ for element in el_list]8 C" d: I/ B2 g2 I5 M9 F$ l
my_str = ''. T* @! z) y7 [: t$ A
range_arr = range_arr if range_arr else [random.randrange(0, len(maps) - 1, 1)]
0 z8 {. G( r. p: Y! a$ R. j for i, i_str in enumerate(maps):
G3 r& ]! Z* A' P% M# Y& m if i in range_arr:: o; |$ o7 ?) F+ [$ t9 s
i_str = re.sub(r'<a[^>]+?href=\"sound\:.*\.mp3\".*</a>', '', i_str).strip()7 j$ E. m1 A* F: J1 w
my_str = my_str + '<li>' + i_str + '</li>'
" H, `2 L7 O+ u# z; q# Q b8 I return self._css(my_str)
9 q# S8 _. B0 f return '', S: O% Q6 [* s* Z0 l$ [
+ Q O. d! B, Z7 c2 S: x1 e
def _range_sentence_audio(self, range_arr=None):
9 ~5 T0 a7 m2 ~ m = re.findall(r'<span class="example"\s*.*>\s*.*<\/span>', self.get_html())0 _ ]2 i" P) _/ g; x# d; _
if m:; z% t( m8 ~& s. {9 K
soup = parse_html(m[0])
% l* T0 f0 S8 F1 B% e/ S el_list = soup.findAll('span', {'class':'example'})% L3 v' U" O/ {1 t+ g
if el_list:
: @6 s6 V+ L1 E maps = []
/ X% ^% n0 _6 D$ y( T6 u. ] for element in el_list:
# v3 W$ Q; S& H i_str = ''
; ?) @) m; [, K9 E/ o$ w0 G; t for content in element.contents:; W- l3 r2 |* b" D+ w9 ]$ z
i_str = i_str + str(content)* v2 ^) l7 h, \3 L* j+ y+ T
sound = re.search(r'<a[^>]+?href=\"sound\:\/(.*?\.mp3)\".*</a>', i_str)
( [1 G7 t8 G2 s) T( f, h if sound:/ Q) ]9 R0 r- h k3 g( |! n
maps.append([sound, i_str])
$ }+ |7 N$ w- }# o' J my_str = ''
5 A" M% ^5 W* y' E range_arr = range_arr if range_arr else [random.randrange(0, len(maps) - 1, 1)]- E& W: C( P, M( E! n
for i, e in enumerate(maps):
/ X! N, P7 E: u5 M if i in range_arr:
5 |6 Q2 J" `7 T+ B1 p/ A+ f i_str = e[1] y2 E( c) H8 C$ D& _; j: e7 W
sound = e[0]; z' r {7 W& J! l* q- V4 T
mp3 = self._fld_audio(sound.groups()[0])
1 m N5 i( w/ Q; c9 G* n2 \ i_str = re.sub(r'<a[^>]+?href=\"sound\:.*\.mp3\".*</a>', '', i_str).strip()
) T. v* l+ \, q' ] my_str = my_str + '<li>' + i_str + ' ' + mp3 + '</li>'& ]+ Z. N! Z d4 m) o
return self._css(my_str)
) A4 j6 G$ |, h( G" l0 o return ''1 W! K( f& O( ^; p5 m, N. `
! ^& A! h/ h) Z1 n, C: F @export([u'额外例句', u'Extra Examples'])
& w) e8 K8 [/ { C$ B. j# K def fld_extra_examples(self):
) @1 b$ O8 A3 q& T+ r7 y- I# C lst = re.findall(r'href="/(@examples_.*?)\">.*?<', self.get_html())# V& W/ [) E2 x- C
if lst:4 L b$ v9 x+ n8 K
str_content = u''
. r, o/ z& C1 O3 J2 R for m in lst:
" q5 x# d7 e* H f' M content = self.builder.mdx_lookup(m)# C" G& S5 g& I Y+ |
if len(content) > 0:* \+ M8 d4 O) n
for c in content:
6 M# ?' Y/ j6 q4 V9 B str_content += c.replace("\r\n","").replace("entry:/","")
" b; J+ C0 Y! W1 }9 @ { return self._css(str_content) y' K) R7 a( J
return ''
7 ^2 L& v& [0 Y( R+ _
% Z% U% c+ @- |6 _ @with_styles(cssfile='_ldoce6.css')9 Q3 n p ^2 c' f& e& [
def _css(self, val):
0 J$ w- {0 s$ U return val
! U) M; k' G, k* v1 m5 G4 Q7 b ---------------------; L8 w" I: ?8 N2 j( O5 h; i
" r, V! |3 s. k2 O3 g- b
谢谢各位
, E: o& E- h$ J. v
( G' Q L0 c! m: I* t; k( D
5 A$ C0 @% ?$ [ |
|