Merge pull request #367 from Aquafina-water-bottle/master

Added various calls for model fields (getting & setting font, setting description)
This commit is contained in:
Alexei Yatskov 2022-12-29 11:42:01 -08:00 committed by GitHub
commit 7234914d44
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 259 additions and 27 deletions

109
README.md
View File

@ -1865,6 +1865,38 @@ corresponding to when the API was available for use.
} }
``` ```
* **modelFieldFonts**
Gets the complete list of fonts along with their font sizes.
*Sample request*:
```json
{
"action": "modelFieldFonts",
"version": 6,
"params": {
"modelName": "Basic"
}
}
```
*Sample result*:
```json
{
"result": {
"Front": {
"font": "Arial",
"size": 20
},
"Back": {
"font": "Arial",
"size": 20
}
},
"error": null
}
```
* **modelFieldsOnTemplates** * **modelFieldsOnTemplates**
Returns an object indicating the fields on the question and answer side of each card template for the given model Returns an object indicating the fields on the question and answer side of each card template for the given model
@ -2238,6 +2270,83 @@ corresponding to when the API was available for use.
} }
``` ```
* **modelFieldSetFont**
Sets the font for a field within a given model.
*Sample Request*:
```json
{
"action": "modelFieldSetFont",
"version": 6,
"params": {
"modelName": "Basic",
"fieldName": "Front",
"font": "Courier"
}
}
```
*Sample result*:
```json
{
"result": null,
"error": null
}
```
* **modelFieldSetFontSize**
Sets the font size for a field within a given model.
*Sample Request*:
```json
{
"action": "modelFieldSetFont",
"version": 6,
"params": {
"modelName": "Basic",
"fieldName": "Front",
"fontSize": 10
}
}
```
*Sample result*:
```json
{
"result": null,
"error": null
}
```
* **modelFieldSetDescription**
Sets the description (the text seen in the gui editor when a field is empty) for a field within a given model.
Older versions of Anki (2.1.49 and below) do not have field descriptions. In that case, this will return with `false`.
*Sample Request*:
```json
{
"action": "modelFieldSetDescription",
"version": 6,
"params": {
"modelName": "Basic",
"fieldName": "Front",
"description": "example field description"
}
}
```
*Sample result*:
```json
{
"result": true,
"error": null
}
```
#### Note Actions #### Note Actions
* **addNote** * **addNote**

View File

@ -189,6 +189,22 @@ class AnkiConnect:
return media return media
def getModel(self, modelName):
model = self.collection().models.byName(modelName)
if model is None:
raise Exception('model was not found: {}'.format(modelName))
return model
def getField(self, modelName, fieldName):
model = self.getModel(modelName)
fieldMap = self.collection().models.fieldMap(model)
if fieldName not in fieldMap:
raise Exception('field was not found in {}: {}'.format(modelName, fieldName))
return fieldMap[fieldName][1]
def startEditing(self): def startEditing(self):
self.window().requireReset() self.window().requireReset()
@ -1082,6 +1098,20 @@ class AnkiConnect:
return ['' for field in model['flds']] return ['' for field in model['flds']]
@util.api()
def modelFieldFonts(self, modelName):
model = self.getModel(modelName)
fonts = {}
for field in model['flds']:
fonts[field['name']] = {
'font': field['font'],
'size': field['size'],
}
return fonts
@util.api() @util.api()
def modelFieldsOnTemplates(self, modelName): def modelFieldsOnTemplates(self, modelName):
@ -1202,14 +1232,8 @@ class AnkiConnect:
@util.api() @util.api()
def modelFieldRename(self, modelName, oldFieldName, newFieldName): def modelFieldRename(self, modelName, oldFieldName, newFieldName):
mm = self.collection().models mm = self.collection().models
model = mm.byName(modelName) model = self.getModel(modelName)
if model is None: field = self.getField(modelName, oldFieldName)
raise Exception('model was not found: {}'.format(modelName))
fieldMap = mm.fieldMap(model)
if oldFieldName not in fieldMap:
raise Exception('field was not found in {}: {}'.format(modelName, oldFieldName))
field = fieldMap[oldFieldName][1]
mm.renameField(model, field, newFieldName) mm.renameField(model, field, newFieldName)
@ -1219,14 +1243,8 @@ class AnkiConnect:
@util.api() @util.api()
def modelFieldReposition(self, modelName, fieldName, index): def modelFieldReposition(self, modelName, fieldName, index):
mm = self.collection().models mm = self.collection().models
model = mm.byName(modelName) model = self.getModel(modelName)
if model is None: field = self.getField(modelName, fieldName)
raise Exception('model was not found: {}'.format(modelName))
fieldMap = mm.fieldMap(model)
if fieldName not in fieldMap:
raise Exception('field was not found in {}: {}'.format(modelName, fieldName))
field = fieldMap[fieldName][1]
mm.repositionField(model, field, index) mm.repositionField(model, field, index)
@ -1236,9 +1254,7 @@ class AnkiConnect:
@util.api() @util.api()
def modelFieldAdd(self, modelName, fieldName, index=None): def modelFieldAdd(self, modelName, fieldName, index=None):
mm = self.collection().models mm = self.collection().models
model = mm.byName(modelName) model = self.getModel(modelName)
if model is None:
raise Exception('model was not found: {}'.format(modelName))
# only adds the field if it doesn't already exist # only adds the field if it doesn't already exist
fieldMap = mm.fieldMap(model) fieldMap = mm.fieldMap(model)
@ -1258,20 +1274,58 @@ class AnkiConnect:
@util.api() @util.api()
def modelFieldRemove(self, modelName, fieldName): def modelFieldRemove(self, modelName, fieldName):
mm = self.collection().models mm = self.collection().models
model = mm.byName(modelName) model = self.getModel(modelName)
if model is None: field = self.getField(modelName, fieldName)
raise Exception('model was not found: {}'.format(modelName))
fieldMap = mm.fieldMap(model)
if fieldName not in fieldMap:
raise Exception('field was not found in {}: {}'.format(modelName, fieldName))
field = fieldMap[fieldName][1]
mm.removeField(model, field) mm.removeField(model, field)
self.save_model(mm, model) self.save_model(mm, model)
@util.api()
def modelFieldSetFont(self, modelName, fieldName, font):
mm = self.collection().models
model = self.getModel(modelName)
field = self.getField(modelName, fieldName)
if not isinstance(font, str):
raise Exception('font should be a string: {}'.format(font))
field['font'] = font
self.save_model(mm, model)
@util.api()
def modelFieldSetFontSize(self, modelName, fieldName, fontSize):
mm = self.collection().models
model = self.getModel(modelName)
field = self.getField(modelName, fieldName)
if not isinstance(fontSize, int):
raise Exception('fontSize should be an integer: {}'.format(fontSize))
field['size'] = fontSize
self.save_model(mm, model)
@util.api()
def modelFieldSetDescription(self, modelName, fieldName, description):
mm = self.collection().models
model = self.getModel(modelName)
field = self.getField(modelName, fieldName)
if not isinstance(description, str):
raise Exception('description should be a string: {}'.format(description))
if 'description' in field: # older versions do not have the 'description' key
field['description'] = description
self.save_model(mm, model)
return True
return False
@util.api() @util.api()
def deckNameFromId(self, deckId): def deckNameFromId(self, deckId):
deck = self.collection().decks.get(deckId) deck = self.collection().decks.get(deckId)

View File

@ -1,4 +1,5 @@
from conftest import ac from conftest import ac
from plugin import anki_version
def test_modelNames(setup): def test_modelNames(setup):
@ -21,6 +22,20 @@ def test_modelFieldDescriptions(setup):
assert result == ["", ""] assert result == ["", ""]
def test_modelFieldFonts(setup):
result = ac.modelFieldFonts(modelName="test_model")
assert result == {
"field1": {
"font": "Arial",
"size": 20,
},
"field2": {
"font": "Arial",
"size": 20,
},
}
def test_modelFieldsOnTemplates(setup): def test_modelFieldsOnTemplates(setup):
result = ac.modelFieldsOnTemplates(modelName="test_model") result = ac.modelFieldsOnTemplates(modelName="test_model")
assert result == { assert result == {
@ -172,3 +187,57 @@ class TestModelFieldNames:
result = ac.modelFieldNames(modelName="test_model") result = ac.modelFieldNames(modelName="test_model")
assert result == ["field2"] assert result == ["field2"]
def test_modelFieldSetFont(self, setup):
ac.modelFieldSetFont(
modelName="test_model",
fieldName="field1",
font="Courier",
)
result = ac.modelFieldFonts(modelName="test_model")
assert result == {
"field1": {
"font": "Courier",
"size": 20,
},
"field2": {
"font": "Arial",
"size": 20,
},
}
def test_modelFieldSetFontSize(self, setup):
ac.modelFieldSetFontSize(
modelName="test_model",
fieldName="field2",
fontSize=16,
)
result = ac.modelFieldFonts(modelName="test_model")
assert result == {
"field1": {
"font": "Arial",
"size": 20,
},
"field2": {
"font": "Arial",
"size": 16,
},
}
def test_modelFieldSetDescription(self, setup):
set_desc = ac.modelFieldSetDescription(
modelName="test_model",
fieldName="field1",
description="test description",
)
result = ac.modelFieldDescriptions(modelName="test_model")
if anki_version < (2, 1, 50):
assert not set_desc
assert result == ["", ""]
else:
assert set_desc
assert result == ["test description", ""]