Skip to content
This repository has been archived by the owner on Jun 16, 2022. It is now read-only.

Commit

Permalink
Added global template variables
Browse files Browse the repository at this point in the history
  • Loading branch information
ADRFranklin committed Sep 30, 2019
1 parent 61accc4 commit 814c092
Show file tree
Hide file tree
Showing 4 changed files with 120 additions and 72 deletions.
8 changes: 5 additions & 3 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,14 +5,16 @@ extern crate log;
mod plugin;

use std::collections::HashMap;
use crate::plugin::Templates;
use crate::plugin::*;
use samp::initialize_plugin;

initialize_plugin!(
natives: [
Templates::create_template,
Templates::render_template,
Templates::create_template_var,
Templates::make_template_var_int,
Templates::make_template_var_float,
Templates::make_template_var_string,
],
{
let samp_logger = samp::plugin::logger()
Expand All @@ -30,7 +32,7 @@ initialize_plugin!(
Templates {
pool: HashMap::new(),
id: 0,
variables: liquid::value::Object::new()
globals: liquid::value::Object::new()
}
}
);
162 changes: 105 additions & 57 deletions src/plugin.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,14 @@
use std::collections::HashMap;
use liquid::value::Object;
use liquid::value::Value;
use log::error;
use samp::native;
use samp::prelude::*;
use samp::{native};
use log::{error};

use std::collections::HashMap;

pub struct Templates {
pub pool: HashMap<i32, liquid::Template>,
pub id: i32,
pub variables: liquid::value::Object
pub globals: Object,
}

#[derive(Debug)]
Expand Down Expand Up @@ -47,11 +48,7 @@ impl Templates {
}

#[native(raw, name = "RenderTemplate")]
pub fn render_template(
&mut self,
_: &Amx,
mut params: samp::args::Args
) -> AmxResult<i32> {
pub fn render_template(&mut self, _: &Amx, mut params: samp::args::Args) -> AmxResult<i32> {
let arg_count = params.count() - 3;
let pairs = if arg_count == 0 || arg_count % 3 == 0 {
arg_count / 3
Expand All @@ -60,25 +57,25 @@ impl Templates {
return Ok(1);
};

let template_id = params.next::<i32>().unwrap();
let template_id = params.next::<i32>().unwrap();
let t = match self.pool.get(&template_id) {
Some(t) => t,
None => return Ok(2),
};

let output_str = params.next::<UnsizedBuffer>().unwrap();
let output_len = params.next::<usize>().unwrap();
let output_len = params.next::<usize>().unwrap();

let mut variables = self.variables.clone();
let mut variables = self.globals.clone();

for _ in 0..pairs {
for _ in 0..pairs {
let var_type = match params.next::<Ref<i32>>() {
None => {
error!("invalid type expected int");
return Ok(-1);
}
Some(t) => t,
};
};

let key = match params.next::<AmxString>() {
None => {
Expand Down Expand Up @@ -119,54 +116,105 @@ impl Templates {
return Ok(0);
}

#[native(raw, name = "CreateTemplateVar")]
pub fn create_template_var(
#[native(name = "MakeTemplateVarInt")]
pub fn make_template_var_int(
&mut self,
_: &Amx,
mut params: samp::args::Args
namespace: AmxString,
key: AmxString,
value: i32,
) -> AmxResult<i32> {
let arg_count = params.count();
let pairs = if arg_count == 0 || arg_count % 3 == 0 {
arg_count / 3
} else {
error!("invalid variadic argument pattern passed to CreateTemplateVar.");
let namespace_str = namespace.to_string();
if namespace_str.is_empty() {
error!("namespace expects a string, none given.");
return Ok(1);
};
}

for _ in 0..pairs {
let var_type = match params.next::<Ref<i32>>() {
None => {
error!("invalid type expected int");
return Ok(-1);
}
Some(t) => t,
};
let key_str = key.to_string();
if key_str.is_empty() {
error!("key expects a string, none given.");
}

let key = match params.next::<AmxString>() {
None => {
error!("invalid type expected string");
return Ok(-1);
},
Some(k) => k.to_string(),
};
let mut variable: Object = Object::new();
for (key, value) in self.globals.iter() {
if key.to_string() == namespace_str {
variable = value.as_object().unwrap().clone();
break;
}
}

match ArgumentPairType::from_i32(*var_type) {
ArgumentPairType::String => {
let value = params.next::<AmxString>().unwrap().to_string();
self.variables.insert(key.into(), liquid::value::Value::scalar(value));
}
ArgumentPairType::Int => {
let value = params.next::<Ref<i32>>().unwrap();
self.variables.insert(key.into(), liquid::value::Value::scalar(*value));
}
ArgumentPairType::Float => {
let value = params.next::<Ref<f32>>().unwrap();
self.variables.insert(key.into(), liquid::value::Value::scalar(*value as f64));
}
_ => return Ok(3),
};
variable.insert(key_str.into(), Value::scalar(value));
self.globals
.insert(namespace_str.into(), Value::Object(variable));

return Ok(0);
}

#[native(name = "MakeTemplateVarFloat")]
pub fn make_template_var_float(
&mut self,
_: &Amx,
namespace: AmxString,
key: AmxString,
value: f32,
) -> AmxResult<i32> {
let namespace_str = namespace.to_string();
if namespace_str.is_empty() {
error!("namespace expects a string, none given.");
return Ok(1);
}

let key_str = key.to_string();
if key_str.is_empty() {
error!("key expects a string, none given.");
}

let mut variable: Object = Object::new();
for (key, value) in self.globals.iter() {
if key.to_string() == namespace_str {
variable = value.as_object().unwrap().clone();
break;
}
}

variable.insert(key_str.into(), Value::scalar(value as f64));
self.globals
.insert(namespace_str.into(), Value::Object(variable));

return Ok(0);
}

#[native(name = "MakeTemplateVarString")]
pub fn make_template_var_string(
&mut self,
_: &Amx,
namespace: AmxString,
key: AmxString,
value: AmxString,
) -> AmxResult<i32> {
let namespace_str = namespace.to_string();
if namespace_str.is_empty() {
error!("namespace expects a string, none given.");
return Ok(1);
}

let key_str = key.to_string();
if key_str.is_empty() {
error!("key expects a string, none given.");
}

let mut variable: Object = Object::new();
for (key, value) in self.globals.iter() {
if key.to_string() == namespace_str {
variable = value.as_object().unwrap().clone();
break;
}
}

variable.insert(key_str.into(), Value::scalar(value.to_string()));
self.globals
.insert(namespace_str.into(), Value::Object(variable));

return Ok(0);
}

Expand All @@ -175,16 +223,16 @@ impl Templates {
self.pool.insert(self.id, template);
self.id
}
}
}

impl Default for Templates {
fn default() -> Self {
Templates {
pool: HashMap::new(),
id: 0,
variables: liquid::value::Object::new()
globals: liquid::value::Object::new(),
}
}
}

impl SampPlugin for Templates {}
impl SampPlugin for Templates {}
4 changes: 3 additions & 1 deletion templates.inc
Original file line number Diff line number Diff line change
Expand Up @@ -21,4 +21,6 @@ enum {

native Template:CreateTemplate(const template[]);
native RenderTemplate(Template:id, dest[], len, ...);
native CreateTemplateVar(...);
native MakeTemplateVarInt(const namespace[], const key[], value);
native MakeTemplateVarFloat(const namespace[], const key[], Float:value);
native MakeTemplateVarString(const namespace[], const key[], const value[]);
18 changes: 7 additions & 11 deletions test.pwn
Original file line number Diff line number Diff line change
Expand Up @@ -85,18 +85,14 @@ Test:Assignment() {
}

Test:GlobalVariables() {
CreateTemplateVar(
PAIR_FLOAT("float", 70.5)
);
new Template:t = CreateTemplate("\
String: {{ string }}, Int: {{ int }}, Float: {{ float }}");
MakeTemplateVarString("player", "name", "Southclaws");
MakeTemplateVarInt("player", "id", 3720);
MakeTemplateVarFloat("player", "pos_x", 5.5);
new Template:t = CreateTemplate("Name: {{ player.name }}, ID: {{ player.id }}, Pos X: {{ player.pos_x }}");
new rendered[64];
new ret = RenderTemplate(t, rendered, sizeof rendered,
PAIR_STR("string", "Southclaws"),
PAIR_INT("int", 50)
);
new ret = RenderTemplate(t, rendered, sizeof rendered);

printf("ret: %d rendered: '%s'", ret, rendered);
ASSERT(ret == 0);
ASSERT(strcmp(rendered, "String: Southclaws, Int: 50, Float: 70.5") == 0);
}
ASSERT(strcmp(rendered, "Name: Southclaws, ID: 3720, Pos X: 5.5") == 0);
}

0 comments on commit 814c092

Please sign in to comment.